<!DOCTYPE html>
<html lang="zh-CN">
<head>
  <meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=2">
<meta name="theme-color" content="#222">
<meta name="generator" content="Hexo 5.4.0">
  <link rel="apple-touch-icon" sizes="180x180" href="/images/M.png">
  <link rel="icon" type="image/png" sizes="32x32" href="/images/M.png">
  <link rel="icon" type="image/png" sizes="16x16" href="/images/M.png">

<link rel="stylesheet" href="/css/main.css">


<link rel="stylesheet" href="/lib/font-awesome/css/all.min.css">
  <link rel="stylesheet" href="/lib/pace/pace-theme-minimal.min.css">
  <script src="/lib/pace/pace.min.js"></script>

<script id="hexo-configurations">
    var NexT = window.NexT || {};
    var CONFIG = {"hostname":"maureen-liu.gitee.io","root":"/","scheme":"Gemini","version":"7.8.0","exturl":false,"sidebar":{"position":"left","display":"post","padding":18,"offset":12,"onmobile":false},"copycode":{"enable":true,"show_result":true,"style":null},"back2top":{"enable":true,"sidebar":true,"scrollpercent":true},"bookmark":{"enable":false,"color":"#222","save":"auto"},"fancybox":false,"mediumzoom":false,"lazyload":false,"pangu":false,"comments":{"style":"tabs","active":"valine","storage":true,"lazyload":false,"nav":null,"activeClass":"valine"},"algolia":{"hits":{"per_page":10},"labels":{"input_placeholder":"Search for Posts","hits_empty":"We didn't find any results for the search: ${query}","hits_stats":"${hits} results found in ${time} ms"}},"localsearch":{"enable":true,"trigger":"auto","top_n_per_article":1,"unescape":false,"preload":false},"motion":{"enable":true,"async":false,"transition":{"post_block":"fadeIn","post_header":"slideDownIn","post_body":"slideDownIn","coll_header":"slideLeftIn","sidebar":"slideUpIn"}},"path":"search.xml"};
  </script>

  <meta name="description" content="一、C++编程简介  1.1 目标  培养正规的、大气的编程习惯 以良好的方式编写C++ class  【Object Based(基于对象)】  class without pointer members  Complex   class with pointer members  String     学习Classes 之间的关系        【Object Oriented(面向对象)">
<meta property="og:type" content="article">
<meta property="og:title" content="C++面向对象高级编程（part I)">
<meta property="og:url" content="https://maureen-liu.gitee.io/p/46598833.html">
<meta property="og:site_name" content="Maureen&#39;s blog">
<meta property="og:description" content="一、C++编程简介  1.1 目标  培养正规的、大气的编程习惯 以良好的方式编写C++ class  【Object Based(基于对象)】  class without pointer members  Complex   class with pointer members  String     学习Classes 之间的关系        【Object Oriented(面向对象)">
<meta property="og:locale" content="zh_CN">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072135491-898592477.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072135960-817576544.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072136882-1951324518.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072138179-993253164.jpg">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072140554-1904868820.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072141429-1147709930.jpg">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072142491-1868919765.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072143429-834599924.jpg">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072144397-101092297.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211123142036430.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211123142216986.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211123142405289.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211123142456047.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211123142533425.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072150679-661549404.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072151866-568027131.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072152975-499455642.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072153819-476354822.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072154507-992598337.jpg">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072155522-1778110504.jpg">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072156460-97285194.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072157069-1339366981.jpg">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072158257-1593049302.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/20211109172214.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072159600-899134466.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072200882-1527187690-20211107200147177.jpg">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072141429-1147709930-20211123143459701.jpg">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211109185730080.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211109185854717.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211109190728455.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211109191217119.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110163920360.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110164344409.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110164638365.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110165427583.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110165445875.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110165501303.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110165551753.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110170054326.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110170442837.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110170808492.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110170945178.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110172523056.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110173100421.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110173451488.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110173549751.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110174125908.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211111162245490.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211111162645886.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211111165443142.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211111170106431.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211111170756652.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211111170450932.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211111171153783.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112144500930.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112144524538.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112144629197.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112152108133.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112152902829.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112153047677.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112153059476.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112153137944.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112153225125.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112153254396.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112153321664.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112153411747.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112153452805.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112153506135.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112182501634.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112182805328.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112182836985.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211117202637564.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211117203523015.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211117203358710.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211117213319789.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211117213758788.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211117214713958.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211117220007249.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211117220050313.png">
<meta property="og:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211117220106586.png">
<meta property="article:published_time" content="2021-11-23T05:57:40.000Z">
<meta property="article:modified_time" content="2021-11-23T08:48:45.268Z">
<meta property="article:author" content="Maureen">
<meta property="article:tag" content="侯捷">
<meta name="twitter:card" content="summary">
<meta name="twitter:image" content="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072135491-898592477.png">

<link rel="canonical" href="https://maureen-liu.gitee.io/p/46598833.html">


<script id="page-configurations">
  // https://hexo.io/docs/variables.html
  CONFIG.page = {
    sidebar: "",
    isHome : false,
    isPost : true,
    lang   : 'zh-CN'
  };
</script>
<script src="/lib/fireworks.js"></script>
  <title>C++面向对象高级编程（part I) | Maureen's blog</title>
  






  <noscript>
  <style>
  .use-motion .brand,
  .use-motion .menu-item,
  .sidebar-inner,
  .use-motion .post-block,
  .use-motion .pagination,
  .use-motion .comments,
  .use-motion .post-header,
  .use-motion .post-body,
  .use-motion .collection-header { opacity: initial; }

  .use-motion .site-title,
  .use-motion .site-subtitle {
    opacity: initial;
    top: initial;
  }

  .use-motion .logo-line-before i { left: initial; }
  .use-motion .logo-line-after i { right: initial; }
  </style>
</noscript>

</head>

<body itemscope itemtype="http://schema.org/WebPage">
  <div class="container use-motion">
    <div class="headband"></div>

    <header class="header" itemscope itemtype="http://schema.org/WPHeader">
      <div class="header-inner"><div class="site-brand-container">
  <div class="site-nav-toggle">
    <div class="toggle" aria-label="切换导航栏">
      <span class="toggle-line toggle-line-first"></span>
      <span class="toggle-line toggle-line-middle"></span>
      <span class="toggle-line toggle-line-last"></span>
    </div>
  </div>

  <div class="site-meta">

    <a href="/" class="brand" rel="start">
      <span class="logo-line-before"><i></i></span>
      <h1 class="site-title">Maureen's blog</h1>
      <span class="logo-line-after"><i></i></span>
    </a>
      <p class="site-subtitle" itemprop="description">记录学习的点点滴滴</p>
  </div>

  <div class="site-nav-right">
    <div class="toggle popup-trigger">
        <i class="fa fa-search fa-fw fa-lg"></i>
    </div>
  </div>
</div>




<nav class="site-nav">
  <ul id="menu" class="main-menu menu">
        <li class="menu-item menu-item-home">

    <a href="/" rel="section"><i class="fa fa-home fa-fw"></i>首页</a>

  </li>
        <li class="menu-item menu-item-tags">

    <a href="/tags/" rel="section"><i class="fa fa-tags fa-fw"></i>标签</a>

  </li>
        <li class="menu-item menu-item-categories">

    <a href="/categories/" rel="section"><i class="fa fa-th fa-fw"></i>分类</a>

  </li>
        <li class="menu-item menu-item-archives">

    <a href="/archives/" rel="section"><i class="fa fa-archive fa-fw"></i>归档</a>

  </li>
      <li class="menu-item menu-item-search">
        <a role="button" class="popup-trigger"><i class="fa fa-search fa-fw"></i>搜索
        </a>
      </li>
  </ul>
</nav>



  <div class="search-pop-overlay">
    <div class="popup search-popup">
        <div class="search-header">
  <span class="search-icon">
    <i class="fa fa-search"></i>
  </span>
  <div class="search-input-container">
    <input autocomplete="off" autocapitalize="off"
           placeholder="搜索..." spellcheck="false"
           type="search" class="search-input">
  </div>
  <span class="popup-btn-close">
    <i class="fa fa-times-circle"></i>
  </span>
</div>
<div id="search-result">
  <div id="no-result">
    <i class="fa fa-spinner fa-pulse fa-5x fa-fw"></i>
  </div>
</div>

    </div>
  </div>

</div>
    </header>

    


    <main class="main">
      <div class="main-inner">
        <div class="content-wrap">
          

          <div class="content post posts-expand">
            

    
  
  
  <article itemscope itemtype="http://schema.org/Article" class="post-block" lang="zh-CN">
    <link itemprop="mainEntityOfPage" href="https://maureen-liu.gitee.io/p/46598833.html">

    <span hidden itemprop="author" itemscope itemtype="http://schema.org/Person">
      <meta itemprop="image" content="/images/stan.jpeg">
      <meta itemprop="name" content="Maureen">
      <meta itemprop="description" content="心之所向，素履以往">
    </span>

    <span hidden itemprop="publisher" itemscope itemtype="http://schema.org/Organization">
      <meta itemprop="name" content="Maureen's blog">
    </span>
      <header class="post-header">
        <h1 class="post-title" itemprop="name headline">
          C++面向对象高级编程（part I)
        </h1>

        <div class="post-meta">
            <span class="post-meta-item">
              <span class="post-meta-item-icon">
                <i class="far fa-calendar"></i>
              </span>
              <span class="post-meta-item-text">发表于</span>
              

              <time title="创建时间：2021-11-23 13:57:40 / 修改时间：16:48:45" itemprop="dateCreated datePublished" datetime="2021-11-23T13:57:40+08:00">2021-11-23</time>
            </span>
            <span class="post-meta-item">
              <span class="post-meta-item-icon">
                <i class="far fa-folder"></i>
              </span>
              <span class="post-meta-item-text">分类于</span>
                <span itemprop="about" itemscope itemtype="http://schema.org/Thing">
                  <a href="/categories/C/" itemprop="url" rel="index"><span itemprop="name">C++</span></a>
                </span>
                  ，
                <span itemprop="about" itemscope itemtype="http://schema.org/Thing">
                  <a href="/categories/C/%E9%9D%A2%E5%90%91%E5%AF%B9%E8%B1%A1%E9%AB%98%E7%BA%A7%E5%BC%80%E5%8F%91/" itemprop="url" rel="index"><span itemprop="name">面向对象高级开发</span></a>
                </span>
            </span>

          
            <span class="post-meta-item" title="阅读次数" id="busuanzi_container_page_pv" style="display: none;">
              <span class="post-meta-item-icon">
                <i class="fa fa-eye"></i>
              </span>
              <span class="post-meta-item-text">阅读次数：</span>
              <span id="busuanzi_value_page_pv"></span>
            </span>
  
  <span class="post-meta-item">
    
      <span class="post-meta-item-icon">
        <i class="far fa-comment"></i>
      </span>
      <span class="post-meta-item-text">Valine：</span>
    
    <a title="valine" href="/p/46598833.html#valine-comments" itemprop="discussionUrl">
      <span class="post-comments-count valine-comment-count" data-xid="/p/46598833.html" itemprop="commentCount"></span>
    </a>
  </span>
  
  <br>
            <span class="post-meta-item" title="本文字数">
              <span class="post-meta-item-icon">
                <i class="far fa-file-word"></i>
              </span>
                <span class="post-meta-item-text">本文字数：</span>
              <span>16k</span>
            </span>
            <span class="post-meta-item" title="阅读时长">
              <span class="post-meta-item-icon">
                <i class="far fa-clock"></i>
              </span>
                <span class="post-meta-item-text">阅读时长 &asymp;</span>
              <span>15 分钟</span>
            </span>

        </div>
      </header>

    
    
    
    <div class="post-body" itemprop="articleBody">
      
      
        <h1 id="一-c编程简介"><a class="markdownIt-Anchor" href="#一-c编程简介"></a> 一、C++编程简介</h1>
<h2 id="11-目标"><a class="markdownIt-Anchor" href="#11-目标"></a> 1.1 目标</h2>
<ul>
<li>培养正规的、大气的编程习惯</li>
<li>以良好的方式编写C++ class  【<mark>Object Based(基于对象)</mark>】
<ul>
<li>class without pointer members
<ul>
<li>Complex</li>
</ul>
</li>
<li>class with pointer members
<ul>
<li>String</li>
</ul>
</li>
</ul>
</li>
<li>学习Classes 之间的关系        【<mark>Object Oriented(面向对象)</mark>】
<ul>
<li>继承（inheritance）</li>
<li>复合（composition）</li>
<li>委托（delegation）</li>
</ul>
</li>
</ul>
<span id="more"></span>
<h2 id="12-c-的历史"><a class="markdownIt-Anchor" href="#12-c-的历史"></a> 1.2 C++ 的历史</h2>
<ul>
<li>
<p>B语言（1969）</p>
</li>
<li>
<p>C语言（1972）</p>
</li>
<li>
<p>C++ 语言 （1983）</p>
<p>（new C -&gt; C with Class -&gt; C++)</p>
</li>
<li>
<p>Java 语言</p>
</li>
<li>
<p>C# 语言</p>
</li>
</ul>
<h2 id="13-c-演化"><a class="markdownIt-Anchor" href="#13-c-演化"></a> 1.3 C++ 演化</h2>
<ul>
<li><strong>C++ 98 （1.0）</strong></li>
<li>C++ 03 （TR1, Technical Report 1）</li>
<li><strong>C++ 11 （2.0）</strong></li>
<li>C++ 14</li>
</ul>
<p><span style="color:red">C++ = C<ins>语言 + C</ins>标准库</span></p>
<p>推荐书籍：</p>
<ul>
<li>《C++ Primer》</li>
<li>《THE C++ PROGRAMMING LANGUAGE》</li>
<li>《Effective C++》</li>
<li>《The C++ Standard Library》</li>
<li>《STL 源码剖析》</li>
</ul>
<h1 id="二-头文件与类声明"><a class="markdownIt-Anchor" href="#二-头文件与类声明"></a> 二、头文件与类声明</h1>
<h2 id="21-c-vs-c-关于数据和函数"><a class="markdownIt-Anchor" href="#21-c-vs-c-关于数据和函数"></a> 2.1 C vs. C++, 关于数据和函数</h2>
<ul>
<li>C语言：语言没有关键，数据必须是全局的</li>
</ul>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072135491-898592477.png" alt="img"></p>
<ul>
<li>C++：增强版struct；数据和函数包在一起；数据之间不会混杂</li>
</ul>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072135960-817576544.png" alt="img"></p>
<h2 id="22-c关于数据和函数"><a class="markdownIt-Anchor" href="#22-c关于数据和函数"></a> 2.2 C++，关于数据和函数</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072136882-1951324518.png" alt="img"></p>
<h2 id="23-object-bases基于对象-vs-object-oriented面向对象"><a class="markdownIt-Anchor" href="#23-object-bases基于对象-vs-object-oriented面向对象"></a> 2.3 Object Bases(基于对象) vs. Object Oriented(面向对象)</h2>
<ul>
<li>Object Based：面向的是单一 class 的设计</li>
<li>Object Oriented：面对的是多重 classes 的设计，classes 和 classes 之间的关系</li>
</ul>
<p>Classes 的两个经典分类：</p>
<ul>
<li>Class without pointer member(s)：Complex</li>
<li>Class with pointer member(s)：String</li>
</ul>
<h2 id="24-c-programs-代码基本形式"><a class="markdownIt-Anchor" href="#24-c-programs-代码基本形式"></a> 2.4 C++ programs 代码基本形式</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072138179-993253164.jpg" alt="img"></p>
<p>延伸文件名（extension file name）即文件扩展名不一定是 <code>.h</code> 或 <code>.cpp</code>，也可能是 <code>.hpp</code> 或其它或甚至无延伸名。</p>
<h2 id="25-header头文件的布局"><a class="markdownIt-Anchor" href="#25-header头文件的布局"></a> 2.5 Header(头文件)的布局</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072140554-1904868820.png" alt="img"></p>
<h2 id="26-class的声明declaration"><a class="markdownIt-Anchor" href="#26-class的声明declaration"></a> 2.6 class的声明（declaration）</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072141429-1147709930.jpg" alt="img"></p>
<h2 id="27-class-template模板简介"><a class="markdownIt-Anchor" href="#27-class-template模板简介"></a> 2.7 class template（模板）简介</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072142491-1868919765.png" alt="img"></p>
<p>实部和虚部的类型在使用的时候才确定。</p>
<h2 id="28-inline内联函数"><a class="markdownIt-Anchor" href="#28-inline内联函数"></a> 2.8 inline（内联）函数</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072143429-834599924.jpg" alt="img"></p>
<p>即使写了<code>inline</code> 关键字，但是函数最终是否能成为 <code>inline</code>，由编译器决定。</p>
<h2 id="29-access-level访问级别"><a class="markdownIt-Anchor" href="#29-access-level访问级别"></a> 2.9 access level（访问级别）</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072144397-101092297.png" alt="img"></p>
<p>所有的数据都放在 <code>private</code>，如果函数是要被外界调用的就放在<code>public</code>，若不打算被外界调用则放在 <code>private</code>。</p>
<p>class body内的 <code>public</code> 和 <code>private</code> 可以交错地出现，并不是只能分为两段，比如：</p>
<figure class="highlight cpp"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">complex</span> &#123;</span></span><br><span class="line"><span class="keyword">private</span>:</span><br><span class="line">    ...</span><br><span class="line"><span class="keyword">public</span>:</span><br><span class="line">    ...</span><br><span class="line"><span class="keyword">private</span>:</span><br><span class="line">    ...</span><br><span class="line"><span class="keyword">public</span>:</span><br><span class="line">    ...</span><br><span class="line">&#125;;</span><br></pre></td></tr></table></figure>
<h1 id="三-构造函数"><a class="markdownIt-Anchor" href="#三-构造函数"></a> 三、构造函数</h1>
<h2 id="31-constructorctor构造函数"><a class="markdownIt-Anchor" href="#31-constructorctor构造函数"></a> 3.1 constructor（ctor，构造函数）</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211123142036430.png" alt="image-20211123142036430"></p>
<ul>
<li>构造函数没有返回值类型；</li>
<li>构造函数的函数名必须和类名一致；</li>
<li>构造函数的参数可以有默认值；</li>
<li>只有构造函数才有初始列表，使用初始列表进行数据的初始化比使用赋值进行值的设定的效率更高；</li>
<li>本类中没有指针变量，一般这种没有指针的类多半不需要写析构函数。</li>
</ul>
<h2 id="32-构造函数可以重载overloading"><a class="markdownIt-Anchor" href="#32-构造函数可以重载overloading"></a> 3.2 构造函数可以重载（overloading）</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211123142216986.png" alt="image-20211123142216986"></p>
<ul>
<li>同名函数编译后的实际名称是不同的，取决于编译器；</li>
<li>上图中的②的存在时不行的，会与 ① 的构造函数发生冲突，右侧构造对象的是时候不知道调用哪个</li>
</ul>
<h2 id="33-constructorctors构造函数被放在-span-stylecolorredprivatespan-区"><a class="markdownIt-Anchor" href="#33-constructorctors构造函数被放在-span-stylecolorredprivatespan-区"></a> 3.3 constructor(ctors,构造函数）被放在 <span style="color:red">private</span> 区</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211123142405289.png" alt="image-20211123142405289"></p>
<ul>
<li>构造函数放在 <code>private</code> 区后，是不能被外界直接调用的。</li>
<li>单例模式：有将ctors放在private区的需求</li>
</ul>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211123142456047.png" alt="image-20211123142456047"></p>
<h2 id="34-const-member-functions常量成员函数"><a class="markdownIt-Anchor" href="#34-const-member-functions常量成员函数"></a> 3.4 const member functions（常量成员函数）</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211123142533425.png" alt="image-20211123142533425"></p>
<ul>
<li><code>const</code>修饰成员函数，要在如上图的位置；</li>
<li>不会改变数据内容的函数加上 <code>const</code>；</li>
<li><code>const</code> 对象一定要调用 <code>const</code> 方法。</li>
</ul>
<h1 id="四-参数传递与返回值"><a class="markdownIt-Anchor" href="#四-参数传递与返回值"></a> 四、参数传递与返回值</h1>
<h2 id="41-参数传递upass-span-stylecolorblueby-valuespanu-vs-upass-span-stylecolorblueby-referencespanuspan-stylecolorgreyto-constspan"><a class="markdownIt-Anchor" href="#41-参数传递upass-span-stylecolorblueby-valuespanu-vs-upass-span-stylecolorblueby-referencespanuspan-stylecolorgreyto-constspan"></a> 4.1 参数传递：<u>pass <span style="color:blue">by value</span></u> vs. <u>pass <span style="color:blue">by reference</span></u><span style="color:grey">（to const）</span></h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072150679-661549404.png" alt="img"></p>
<ul>
<li>数据所占内存很大(32位机器上大于4字节)的时候，传地址(32位机器上占4字节)的速度更快；而引用在底层就是指针，传引用就相当于传指针；</li>
<li>参数传递的时候尽量传递引用；</li>
<li>如果传递的参数不希望被函数修改，那么就传 <code>const</code> 引用</li>
</ul>
<h2 id="42-返回值传递return-span-stylecolorblueby-valuespan-vs-return-span-stylecolorblueby-referencespan-span-stylecolorgreyto-constspan"><a class="markdownIt-Anchor" href="#42-返回值传递return-span-stylecolorblueby-valuespan-vs-return-span-stylecolorblueby-referencespan-span-stylecolorgreyto-constspan"></a> 4.2 返回值传递：return <span style="color:blue">by value</span> vs. return <span style="color:blue">by reference</span> <span style="color:grey">(to const)</span></h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072151866-568027131.png" alt="img"></p>
<h2 id="43-friend友元"><a class="markdownIt-Anchor" href="#43-friend友元"></a> 4.3 friend(友元)</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072152975-499455642.png" alt="img"></p>
<h2 id="44-相同-class-的各个-objects-互为-friends友元"><a class="markdownIt-Anchor" href="#44-相同-class-的各个-objects-互为-friends友元"></a> 4.4 相同 class 的各个 objects 互为 friends（友元）</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072153819-476354822.png" alt="img"></p>
<h2 id="45-class-body-外的各种定义definitions"><a class="markdownIt-Anchor" href="#45-class-body-外的各种定义definitions"></a> 4.5 class body 外的各种定义（definitions）</h2>
<ul>
<li>什么情况下可以 pass by reference</li>
<li>什么情况下可以 return by reference</li>
</ul>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072154507-992598337.jpg" alt="img"></p>
<p>运算结果放到一个不存在的空间（变量）中，则不能返回引用，除此之外，都可以返回引用。</p>
<h1 id="五-操作符重载与临时对象"><a class="markdownIt-Anchor" href="#五-操作符重载与临时对象"></a> 五、操作符重载与临时对象</h1>
<h2 id="51-operator-overloading-操作符重载-1成员函数this"><a class="markdownIt-Anchor" href="#51-operator-overloading-操作符重载-1成员函数this"></a> 5.1 operator overloading （操作符重载-1，成员函数）this</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072155522-1778110504.jpg" alt="img"></p>
<ul>
<li>所有的成员函数都有一个隐藏的参数 <code>this</code>，指向调用者。</li>
<li><code>_doapl</code>，do assignment plus，标准库的代码</li>
</ul>
<h2 id="52-return-by-reference语法分析"><a class="markdownIt-Anchor" href="#52-return-by-reference语法分析"></a> 5.2 return by reference语法分析</h2>
<p><u>传递者</u> 无需知道 <u>接受者</u> 是以 <u>reference形式</u> 接收</p>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072156460-97285194.png" alt="img"></p>
<ul>
<li><code>_doapl</code> 函数返回的是 <code>object</code>（指针指向的内容），是个值，但是接收使用的是 <code>complex&amp;</code> 引用；</li>
<li><code>c2 += c1</code>，其中 <code>c1</code> 就是传递者。</li>
</ul>
<h2 id="53-class-body-之外的重定义"><a class="markdownIt-Anchor" href="#53-class-body-之外的重定义"></a> 5.3 class body 之外的重定义</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072157069-1339366981.jpg" alt="img"></p>
<h2 id="54-operator-overloading操作符重载-2-非成员函数无this"><a class="markdownIt-Anchor" href="#54-operator-overloading操作符重载-2-非成员函数无this"></a> 5.4 operator overloading（操作符重载-2， 非成员函数）无this</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072158257-1593049302.png" alt="img"></p>
<ul>
<li>三个全域函数对应的是三种不同的调用情况：复数 + 复数，复数 + 实数，实数 + 复数。</li>
</ul>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/20211109172214.png" alt="img"></p>
<ul>
<li>操作符重载，有两种选择：成员函数或者全局函数，但是 <code>&lt;&lt;</code> 只能写成全局函数；操作符重载是作用在左边的参数上，成员函数默认有个 <code>this</code> 参数，如果写成成员函数，使用的时候就变成了 <code>c1 &lt;&lt; cout</code>，不符合一般的使用习惯，因此 <code>&lt;&lt;</code> 写成全局函数；</li>
<li><code>ostream&amp; operator&lt;&lt;(ostream&amp; os, const complex&amp; x)</code> 函数中的第一个参数 <code>os</code> 不能用 <code>const</code>，因为数据往 <code>os</code> 里丢数据的时候一直都在改变 <code>os</code>;</li>
<li><code>ostream&amp; operator&lt;&lt;(ostream&amp; os, const complex&amp; x)</code> 函数的返回类型不能是 <code>void</code>，因为可能以这种方式使用：<code>cout &lt;&lt; c1 &lt;&lt; conj(c1)</code>，如果返回的是 <code>void</code>，则不能连用 <code>&lt;&lt;</code>。</li>
</ul>
<h2 id="55-temp-object临时对象"><a class="markdownIt-Anchor" href="#55-temp-object临时对象"></a> 5.5 temp object临时对象</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072159600-899134466.png" alt="img"></p>
<ul>
<li>这三个函数得到的结果都是目前不存在的，需要新创建，而且返回后可能被外界使用，而这个新创建的对象返回后需要销毁，所以不能返回引用，而一定要返回值。</li>
<li><mark><code>typename();</code></mark> 用于创建临时对象，比如 <code>complex(x + real(y), imag(y));</code></li>
</ul>
<figure class="highlight cpp"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br></pre></td><td class="code"><pre><span class="line">&#123;</span><br><span class="line">    <span class="built_in"><span class="keyword">int</span></span>(<span class="number">7</span>);</span><br><span class="line">    </span><br><span class="line">    <span class="function">complex <span class="title">c1</span><span class="params">(<span class="number">2</span>, <span class="number">1</span>)</span></span>;</span><br><span class="line">    complex c2;</span><br><span class="line">    <span class="built_in">complex</span>(); <span class="comment">//临时对象</span></span><br><span class="line">    <span class="built_in">complex</span>(<span class="number">4</span>, <span class="number">5</span>); <span class="comment">//临时对象</span></span><br><span class="line">    <span class="comment">//到这里的时候，临时对象的生命到此结束</span></span><br><span class="line">    </span><br><span class="line">    cout &lt;&lt; <span class="built_in">complex</span>(<span class="number">2</span>);</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072200882-1527187690-20211107200147177.jpg" alt="img"></p>
<h2 id="56-小结"><a class="markdownIt-Anchor" href="#56-小结"></a> 5.6 小结</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/809212-20160307072141429-1147709930-20211123143459701.jpg" alt="img"></p>
<p>设计一个 <code>class</code> 要注意的事项：</p>
<ul>
<li>构造函数使用 <strong>初始列表</strong></li>
<li>考虑函数是否要加 <code>const</code></li>
<li>参数的传递尽量使用引用，考虑是否加 <code>const</code></li>
<li>考虑清楚返回值的类型是值还是引用</li>
<li>数据放在 <code>private</code></li>
<li>函数绝大部分放在 <code>public</code></li>
</ul>
<h1 id="六-复习complex类的实现过程"><a class="markdownIt-Anchor" href="#六-复习complex类的实现过程"></a> 六、复习Complex类的实现过程</h1>
<p>下面的程序是来自标准库的函数，去除了某些部分。</p>
<figure class="highlight cpp"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br><span class="line">48</span><br><span class="line">49</span><br><span class="line">50</span><br><span class="line">51</span><br><span class="line">52</span><br><span class="line">53</span><br><span class="line">54</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">/*************************************************************************</span></span><br><span class="line"><span class="comment">	&gt; File Name: complex.h</span></span><br><span class="line"><span class="comment">	&gt; Author: Maureen </span></span><br><span class="line"><span class="comment">	&gt; Mail: Maureen@qq.com </span></span><br><span class="line"><span class="comment">	&gt; Created Time: 二 11/ 9 17:58:17 2021</span></span><br><span class="line"><span class="comment"> ************************************************************************/</span></span><br><span class="line"></span><br><span class="line"><span class="meta">#<span class="meta-keyword">ifndef</span> _COMPLEX_H</span></span><br><span class="line"><span class="meta">#<span class="meta-keyword">define</span> _COMPLEX_H</span></span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">complex</span> &#123;</span></span><br><span class="line"><span class="keyword">public</span>:</span><br><span class="line">    <span class="built_in">complex</span>(<span class="keyword">double</span> r = <span class="number">0</span>, <span class="keyword">double</span> i = <span class="number">0</span>) : <span class="built_in">re</span>(r), <span class="built_in">im</span>(i) &#123;&#125;</span><br><span class="line"></span><br><span class="line">    complex&amp; <span class="keyword">operator</span>+=(<span class="keyword">const</span> complex&amp;);</span><br><span class="line"></span><br><span class="line">    <span class="comment">//函数内部没有修改成员数据，所以加上const</span></span><br><span class="line">    <span class="function"><span class="keyword">double</span> <span class="title">real</span><span class="params">()</span> <span class="keyword">const</span> </span>&#123; <span class="keyword">return</span> re; &#125;</span><br><span class="line">    <span class="function"><span class="keyword">double</span> <span class="title">imag</span><span class="params">()</span> <span class="keyword">const</span> </span>&#123; <span class="keyword">return</span> im; &#125;</span><br><span class="line"><span class="keyword">private</span>:</span><br><span class="line">    <span class="keyword">double</span> re, im;</span><br><span class="line">    <span class="keyword">friend</span> complex&amp; __doapl(complex*, <span class="keyword">const</span> complex&amp;);</span><br><span class="line">&#125;;</span><br><span class="line"></span><br><span class="line"><span class="keyword">inline</span> complex&amp; __doapl(complex* ths, <span class="keyword">const</span> complex&amp; r) &#123;</span><br><span class="line">    ths-&gt;re += r.re;</span><br><span class="line">    ths-&gt;im += r.im;</span><br><span class="line">    <span class="keyword">return</span> *ths;</span><br><span class="line">&#125;</span><br><span class="line"><span class="keyword">inline</span> complex&amp; complex::<span class="keyword">operator</span>+=(<span class="keyword">const</span> complex&amp; r) &#123;</span><br><span class="line">    <span class="keyword">return</span> __doapl(<span class="keyword">this</span>, r);</span><br><span class="line">&#125;</span><br><span class="line"></span><br><span class="line"><span class="comment">//不将operator+设计为类的成员函数，就是因为加法的左右值类型是多样变化的</span></span><br><span class="line"><span class="keyword">inline</span> complex <span class="keyword">operator</span>+(<span class="keyword">const</span> complex&amp; x, <span class="keyword">const</span> complex&amp; y) &#123; <span class="comment">//复数 + 复数</span></span><br><span class="line">    <span class="keyword">return</span> <span class="built_in">complex</span>(<span class="built_in">real</span>(x) + <span class="built_in">real</span>(y), <span class="built_in">imag</span>(x) + <span class="built_in">imag</span>(y)); <span class="comment">//返回的是local object,所以返回值类型必须是值</span></span><br><span class="line">&#125;</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="keyword">inline</span> complex <span class="keyword">operator</span>+(<span class="keyword">const</span> complex&amp; x, <span class="keyword">double</span> y) &#123; <span class="comment">//复数+实数</span></span><br><span class="line">    <span class="keyword">return</span> <span class="built_in">complex</span>(<span class="built_in">real</span>(x) + y, <span class="built_in">imag</span>(x));</span><br><span class="line">&#125;</span><br><span class="line"></span><br><span class="line"><span class="keyword">inline</span> complex <span class="keyword">operator</span>+(<span class="keyword">double</span> x, <span class="keyword">const</span> complex&amp; y) &#123; <span class="comment">//实数+复数</span></span><br><span class="line">    <span class="keyword">return</span> <span class="built_in">complex</span>(x + <span class="built_in">real</span>(y), <span class="built_in">imag</span>(y));</span><br><span class="line">&#125;</span><br><span class="line"></span><br><span class="line"><span class="meta">#<span class="meta-keyword">include</span> <span class="meta-string">&lt;iostream.h&gt;</span></span></span><br><span class="line">ostream&amp; <span class="keyword">operator</span>&lt;&lt;(ostream&amp; os, <span class="keyword">const</span> complex&amp; x) &#123; <span class="comment">//返回值为引用考虑了“连用”</span></span><br><span class="line">    <span class="keyword">return</span> os &lt;&lt; <span class="string">&#x27;(&#x27;</span> &lt;&lt; <span class="built_in">real</span>(x) &lt;&lt; <span class="string">&#x27;,&#x27;</span> &lt;&lt; <span class="built_in">imag</span>(x) &lt;&lt; <span class="string">&#x27;)&#x27;</span>;</span><br><span class="line">&#125;</span><br><span class="line"></span><br><span class="line"><span class="meta">#<span class="meta-keyword">endif</span></span></span><br></pre></td></tr></table></figure>
<h1 id="七-三大函数拷贝构造拷贝赋值析构"><a class="markdownIt-Anchor" href="#七-三大函数拷贝构造拷贝赋值析构"></a> 七、三大函数：拷贝构造，拷贝赋值，析构</h1>
<h2 id="71-class的两个经典分类"><a class="markdownIt-Anchor" href="#71-class的两个经典分类"></a> 7.1 class的两个经典分类</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211109185730080.png" alt="image-20211109185730080"></p>
<p>若类中有指针，如果只是简单的拷贝，那就是指针拷贝，两个指针指向的是同一个空间，所以不能直接拷贝。<mark>如果类中有指针，一定要自己写拷贝构造</mark>。</p>
<h2 id="72-string-class"><a class="markdownIt-Anchor" href="#72-string-class"></a> 7.2 String class</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211109185854717.png" alt="image-20211109185854717"></p>
<h2 id="73-big-three-三个特殊函数"><a class="markdownIt-Anchor" href="#73-big-three-三个特殊函数"></a> 7.3 Big Three, 三个特殊函数</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211109190728455.png" alt="image-20211109190728455"></p>
<ul>
<li>此处使用 <code>char* m_data</code>，就是在使用的时候才指向字符串，就是动态分配的方式；</li>
<li><code>get_c_str()</code> 函数没有修改指针，所以加上 <code>const</code> 。</li>
</ul>
<h3 id="731-ctor和dtor构造函数和析构函数"><a class="markdownIt-Anchor" href="#731-ctor和dtor构造函数和析构函数"></a> 7.3.1 ctor和dtor（构造函数和析构函数）</h3>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211109191217119.png" alt="image-20211109191217119"></p>
<ul>
<li>class中有指针，多半就要进行动态分配；做了动态分配，在的对象死亡后，就要释放掉分配的空间；</li>
<li><code>s1、s2、p</code>这三个字符串都会调用<code>String(const char* str = 0)</code> 这个构造函数，离开作用域之后都会调用析构函数。</li>
</ul>
<h3 id="732-class-with-pointer-members-必须有-copy-ctor和-copy-op"><a class="markdownIt-Anchor" href="#732-class-with-pointer-members-必须有-copy-ctor和-copy-op"></a> 7.3.2 class with pointer members 必须有 copy ctor和 copy op=</h3>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110163920360.png" alt="image-20211110163920360"></p>
<p>使用 <code>default copy ctor</code> 或 <code>default op=</code>是<strong>浅拷贝</strong>，是需要避免的。</p>
<h3 id="733-copy-ctor拷贝构造函数"><a class="markdownIt-Anchor" href="#733-copy-ctor拷贝构造函数"></a> 7.3.3 copy ctor（拷贝构造函数）</h3>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110164344409.png" alt="image-20211110164344409"></p>
<p>此处的</p>
<figure class="highlight cpp"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="function">String <span class="title">s2</span><span class="params">(s1)</span></span>;</span><br><span class="line">String s2 = s1;</span><br></pre></td></tr></table></figure>
<p>意思是一样的，都会调用拷贝构造函数。拷贝构造函数里是<strong>深拷贝</strong>。</p>
<h3 id="734-copy-assignment-operator拷贝赋值函数"><a class="markdownIt-Anchor" href="#734-copy-assignment-operator拷贝赋值函数"></a> 7.3.4 copy assignment operator（拷贝赋值函数）</h3>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110164638365.png" alt="image-20211110164638365"></p>
<p>①②③的流程：</p>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110165427583.png" alt="image-20211110165427583"></p>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110165445875.png" alt="image-20211110165445875"></p>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110165501303.png" alt="image-20211110165501303"></p>
<ul>
<li>一定要在 <code>operator=</code> 中检查是否 selft assignment</li>
</ul>
<p>如果不做 self assignment，就会造成如下问题：</p>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110165551753.png" alt="image-20211110165551753"></p>
<p>检查自我赋值（self assignment）不只是为了效率，还是为了正确性。</p>
<h3 id="735-output函数"><a class="markdownIt-Anchor" href="#735-output函数"></a> 7.3.5 output函数</h3>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110170054326.png" alt="image-20211110170054326"></p>
<p><code>operator&lt;&lt;</code> 不能写成成员函数，否则<code>cout</code>和要输出的内容就会相反。</p>
<h1 id="八-堆-栈与内存管理"><a class="markdownIt-Anchor" href="#八-堆-栈与内存管理"></a> 八、堆、栈与内存管理</h1>
<h2 id="81-所谓-stack栈所谓-heap堆"><a class="markdownIt-Anchor" href="#81-所谓-stack栈所谓-heap堆"></a> 8.1 所谓 stack（栈），所谓 heap（堆）</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110170442837.png" alt="image-20211110170442837"></p>
<h2 id="82-stack-objects的生命期"><a class="markdownIt-Anchor" href="#82-stack-objects的生命期"></a> 8.2 stack objects的生命期</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110170808492.png" alt="image-20211110170808492"></p>
<p>「自动」清理即析构函数会被自动调用。</p>
<h2 id="83-static-local-objects的生命期"><a class="markdownIt-Anchor" href="#83-static-local-objects的生命期"></a> 8.3 static local objects的生命期</h2>
<figure class="highlight cpp"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">Complex</span> &#123;</span> ... &#125;;</span><br><span class="line">...</span><br><span class="line"> </span><br><span class="line">&#123;</span><br><span class="line">    <span class="function"><span class="keyword">static</span> Complex <span class="title">c2</span><span class="params">(<span class="number">1</span>,<span class="number">2</span>)</span></span>;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>
<p><code>c2</code> 便是所谓 <code>static object</code>，其生命在作用域（scope）结束之后仍然存在，直到整个程序结束。</p>
<h2 id="84-global-objects的生命期"><a class="markdownIt-Anchor" href="#84-global-objects的生命期"></a> 8.4 global objects的生命期</h2>
<figure class="highlight cpp"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br></pre></td><td class="code"><pre><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">Complex</span> &#123;</span> ... &#125;;</span><br><span class="line">...</span><br><span class="line"><span class="function">Complex <span class="title">c3</span><span class="params">(<span class="number">1</span>,<span class="number">2</span>)</span></span>;</span><br><span class="line"></span><br><span class="line"><span class="function"><span class="keyword">int</span> <span class="title">main</span><span class="params">()</span> </span></span><br><span class="line"><span class="function"></span>&#123;</span><br><span class="line">    ...</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>
<p><code>c3</code> 便是所谓 <code>global object</code>，其生命在整个程序结束之后才结束。你也可以把它视为一种 <code>static object</code>，其作用域是「整个程序」。</p>
<h2 id="85-heap-objects的生命周期"><a class="markdownIt-Anchor" href="#85-heap-objects的生命周期"></a> 8.5 heap objects的生命周期</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110170945178.png" alt="image-20211110170945178"></p>
<h2 id="86-new先分配memory再调用ctor"><a class="markdownIt-Anchor" href="#86-new先分配memory再调用ctor"></a> 8.6 new：先分配memory，再调用ctor</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110172523056.png" alt="image-20211110172523056"></p>
<ul>
<li><code>pc</code> 是分配的内存的起始位置，也就是 <code>this</code>。</li>
</ul>
<h2 id="87-delete先调用dtor再释放memory"><a class="markdownIt-Anchor" href="#87-delete先调用dtor再释放memory"></a> 8.7 delete：先调用dtor，再释放memory</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110173100421.png" alt="image-20211110173100421"></p>
<h2 id="88-new先分配memory再调用ctor"><a class="markdownIt-Anchor" href="#88-new先分配memory再调用ctor"></a> 8.8 new：先分配memory，再调用ctor</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110173451488.png" alt="image-20211110173451488"></p>
<h2 id="89-delete先调用dtor再释放memory"><a class="markdownIt-Anchor" href="#89-delete先调用dtor再释放memory"></a> 8.9 delete：先调用dtor，再释放memory</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110173549751.png" alt="image-20211110173549751"></p>
<ul>
<li>①将字符串里面动态分配的内存销毁；至于字符串本身，只是一个指针；</li>
<li>②销毁字符串本身，本身是个指针。</li>
</ul>
<h2 id="810-动态分配所得的内存块memory-blockin-vc"><a class="markdownIt-Anchor" href="#810-动态分配所得的内存块memory-blockin-vc"></a> 8.10 动态分配所得的内存块（memory block），in VC</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211110174125908.png" alt="image-20211110174125908"></p>
<p>图中为内存结构，在VC中，分配的内存空间大小都是16的倍数，第一个图中是调试模式下, 每个格表示4Bytes，Complex对象占8个字节，计算得到的结果是52Bytes，不是16的倍数，所以补充12个Bytes的填补字节，凑到64。开头和结尾的<code>00000041</code>，其中的 <code>4</code> 是 64的16进制，<code>1</code>表示这块空间已经给出去了，<code>0</code>表示这块空间空闲。第二个图为非调试模式，对象所占的内存空间。</p>
<h2 id="811-动态分配的array"><a class="markdownIt-Anchor" href="#811-动态分配的array"></a> 8.11 动态分配的array</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211111162245490.png" alt="image-20211111162245490"></p>
<h2 id="812-array-new-一定要搭配-array-delete"><a class="markdownIt-Anchor" href="#812-array-new-一定要搭配-array-delete"></a> 8.12 array new 一定要搭配 array delete</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211111162645886.png" alt="image-20211111162645886"></p>
<p>错误用法<code>delete p;</code>导致出现的内存泄漏是<code>String</code> 类中的指针指向的空间，而非指针本身。</p>
<p>如果是<code>Complex</code> 数组对象，因为其中没有指针，所以就算是使用 <code>delete p;</code> 也是没有问题的。</p>
<p>但是为了万无一失，如果使用了<code>array new</code> 一定要搭配 <code>array delete</code>。</p>
<h1 id="九-复习string类的实现过程"><a class="markdownIt-Anchor" href="#九-复习string类的实现过程"></a> 九、复习String类的实现过程</h1>
<figure class="highlight cpp"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br><span class="line">48</span><br><span class="line">49</span><br><span class="line">50</span><br><span class="line">51</span><br><span class="line">52</span><br><span class="line">53</span><br><span class="line">54</span><br><span class="line">55</span><br><span class="line">56</span><br><span class="line">57</span><br><span class="line">58</span><br><span class="line">59</span><br><span class="line">60</span><br><span class="line">61</span><br><span class="line">62</span><br><span class="line">63</span><br><span class="line">64</span><br><span class="line">65</span><br><span class="line">66</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">/*************************************************************************</span></span><br><span class="line"><span class="comment">	&gt; File Name: String.h</span></span><br><span class="line"><span class="comment">	&gt; Author: Maureen</span></span><br><span class="line"><span class="comment">	&gt; Mail: Maureen@qq.com</span></span><br><span class="line"><span class="comment">	&gt; Created Time: 四 11/11 16:34:55 2021</span></span><br><span class="line"><span class="comment"> ************************************************************************/</span></span><br><span class="line"></span><br><span class="line"><span class="meta">#<span class="meta-keyword">ifndef</span> _STRING_H</span></span><br><span class="line"><span class="meta">#<span class="meta-keyword">define</span> _STRING_H</span></span><br><span class="line"></span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">String</span> &#123;</span></span><br><span class="line"><span class="keyword">public</span>:</span><br><span class="line">    <span class="built_in">String</span>(<span class="keyword">const</span> <span class="keyword">char</span>* cstr = <span class="number">0</span>);</span><br><span class="line">    <span class="built_in">String</span>(<span class="keyword">const</span> String&amp; str);</span><br><span class="line">    String&amp; <span class="keyword">operator</span>=(<span class="keyword">const</span> String&amp; str);</span><br><span class="line">    ~<span class="built_in">String</span>();</span><br><span class="line">    <span class="comment">//函数没有更改m_data，所以加上const</span></span><br><span class="line">    <span class="function"><span class="keyword">char</span>* <span class="title">get_c_str</span><span class="params">()</span> <span class="keyword">const</span> </span>&#123; <span class="keyword">return</span> m_data; &#125;</span><br><span class="line"><span class="keyword">private</span>:</span><br><span class="line">    <span class="comment">//动态分配的方式保存字符串</span></span><br><span class="line">    <span class="keyword">char</span>* m_data;</span><br><span class="line">&#125;;</span><br><span class="line"></span><br><span class="line"><span class="meta">#<span class="meta-keyword">include</span> <span class="meta-string">&lt;string.h&gt;</span></span></span><br><span class="line"></span><br><span class="line"><span class="comment">//建议编译器将函数作为内联函数</span></span><br><span class="line"><span class="function"><span class="keyword">inline</span></span></span><br><span class="line"><span class="function"><span class="title">String::String</span><span class="params">(<span class="keyword">const</span> <span class="keyword">char</span>* cstr = <span class="number">0</span>)</span> </span>&#123;</span><br><span class="line">    <span class="keyword">if</span> (cstr) &#123;</span><br><span class="line">        m_data = <span class="keyword">new</span> <span class="keyword">char</span>[<span class="built_in">strlen</span>(cstr) + <span class="number">1</span>];</span><br><span class="line">        <span class="built_in">strcpy</span>(m_data, cstr);</span><br><span class="line">    &#125; <span class="keyword">else</span> &#123; <span class="comment">//未指定初值</span></span><br><span class="line">        m_data = <span class="keyword">new</span> <span class="keyword">char</span>[<span class="number">1</span>];</span><br><span class="line">        *m_data = <span class="string">&#x27;\0&#x27;</span>;</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="keyword">inline</span></span><br><span class="line">String::~<span class="built_in">String</span>() &#123;</span><br><span class="line">    <span class="comment">//array new搭配array delete</span></span><br><span class="line">    <span class="keyword">delete</span>[] m_data;</span><br><span class="line">&#125;</span><br><span class="line"></span><br><span class="line"><span class="comment">//拷贝构造</span></span><br><span class="line"><span class="function"><span class="keyword">inline</span></span></span><br><span class="line"><span class="function"><span class="title">String::String</span><span class="params">(<span class="keyword">const</span> String&amp; str)</span> </span>&#123;</span><br><span class="line">    m_data = <span class="keyword">new</span> <span class="keyword">char</span>[<span class="built_in">strlen</span>(str.m_data) + <span class="number">1</span>];</span><br><span class="line">    <span class="built_in">strcpy</span>(m_data, str.m_data);</span><br><span class="line">&#125;</span><br><span class="line"></span><br><span class="line"><span class="comment">//拷贝赋值函数</span></span><br><span class="line"><span class="keyword">inline</span></span><br><span class="line">String&amp; String::<span class="keyword">operator</span>=(<span class="keyword">const</span> String&amp; str) &#123; <span class="comment">//Type&amp;，此处的&amp;表示引用</span></span><br><span class="line">    <span class="comment">//考虑自我赋值，必须做</span></span><br><span class="line">    <span class="keyword">if</span> (<span class="keyword">this</span> == &amp;str) <span class="comment">//&amp;obj，此处的&amp;表示取地址，得到obj的指针</span></span><br><span class="line">        <span class="keyword">return</span> *<span class="keyword">this</span>;</span><br><span class="line"></span><br><span class="line">    <span class="comment">//先将本身的东西清除，再分配足够多的空间容纳新的字符串</span></span><br><span class="line">    <span class="keyword">delete</span>[] m_data;</span><br><span class="line">    m_data =  <span class="keyword">new</span> <span class="keyword">char</span>[<span class="built_in">strlen</span>(str.m_data) + <span class="number">1</span>];</span><br><span class="line">    <span class="built_in">strcpy</span>(m_data, str.m_data);</span><br><span class="line">    <span class="keyword">return</span> *<span class="keyword">this</span>; <span class="comment">//考虑到连用，所以要返回引用</span></span><br><span class="line">&#125;</span><br><span class="line"></span><br><span class="line"><span class="meta">#<span class="meta-keyword">endif</span></span></span><br></pre></td></tr></table></figure>
<h1 id="十-扩展补充类模板-函数模板及其它"><a class="markdownIt-Anchor" href="#十-扩展补充类模板-函数模板及其它"></a> 十、扩展补充：类模板、函数模板及其它</h1>
<h2 id="101-进一步补充static"><a class="markdownIt-Anchor" href="#101-进一步补充static"></a> 10.1 进一步补充：static</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211111165443142.png" alt="image-20211111165443142"></p>
<ul>
<li>非<code>static</code> 函数通过传入的 <code>this</code> 指针找到要处理的对象；</li>
<li><code>static</code>数据只有一份；</li>
<li><code>static</code> 函数没有 <code>this</code> 指针；只能处理静态数据。</li>
</ul>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211111170106431.png" alt="image-20211111170106431"></p>
<ul>
<li>静态数据要在类外进行定义。</li>
</ul>
<h2 id="102-进一步补充把ctors放在private区"><a class="markdownIt-Anchor" href="#102-进一步补充把ctors放在private区"></a> 10.2 进一步补充：把ctors放在private区</h2>
<p>创建出来的类只能有一个对象 。</p>
<ul>
<li>第一种写法：</li>
</ul>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211111170756652.png" alt="image-20211111170756652"></p>
<p>缺点：如果不需要A的实例，但是也创建了。</p>
<ul>
<li>第二种写法：</li>
</ul>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211111170450932.png" alt="image-20211111170450932"></p>
<p>函数中的 <code>static</code> 对象，只有当调用了该函数的时候，该对象才会创建；该函数执行后，这个<code>static</code>对象仍然存在。这种写法更好。</p>
<h2 id="103-进一步补充cout"><a class="markdownIt-Anchor" href="#103-进一步补充cout"></a> 10.3 进一步补充：cout</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211111171153783.png" alt="image-20211111171153783"></p>
<h2 id="104-进一步补充class-template类模板"><a class="markdownIt-Anchor" href="#104-进一步补充class-template类模板"></a> 10.4 进一步补充：class template，类模板</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112144500930.png" alt="image-20211112144500930"></p>
<ul>
<li><code>template</code>和<code>typename</code> 都是关键字，<code>template&lt;typename T&gt;</code>告诉编译器当前类型还没有绑定；</li>
<li>用法：<code>complex&lt;double&gt;</code>，编译器会将代码中的 <code>T</code> 替换为 <code>double</code>;</li>
<li>不同的绑定类型会生成不同的代码，模板会造成代码的膨胀，但是这并不是缺点，而是必要的。</li>
</ul>
<h2 id="105-进一步补充function-template函数模板"><a class="markdownIt-Anchor" href="#105-进一步补充function-template函数模板"></a> 10.5 进一步补充：function template，函数模板</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112144524538.png" alt="image-20211112144524538"></p>
<ul>
<li>此处的<code>template &lt;class T&gt;</code> 中的 <code>class</code> 和 <code>typename</code> 是一样的；</li>
<li>使用模板函数的时候不用指出类型，因为编译器会进行<strong>引数推导</strong>。</li>
</ul>
<h2 id="106-进一步补充namespace"><a class="markdownIt-Anchor" href="#106-进一步补充namespace"></a> 10.6 进一步补充：namespace</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112144629197.png" alt="image-20211112144629197"></p>
<h2 id="107-更多细节与深入"><a class="markdownIt-Anchor" href="#107-更多细节与深入"></a> 10.7 更多细节与深入</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112152108133.png" alt="image-20211112152108133"></p>
<h1 id="十一-组合与继承"><a class="markdownIt-Anchor" href="#十一-组合与继承"></a> 十一、组合与继承</h1>
<p>Object Oriented Programming，Object Oriented Design</p>
<p>OOP,OOD</p>
<ul>
<li>Inheritance（继承）</li>
<li>Composition（复合）</li>
<li>Delegation（委托）</li>
</ul>
<h2 id="111-composition复合表示has-a"><a class="markdownIt-Anchor" href="#111-composition复合表示has-a"></a> 11.1 Composition（复合），表示has-a</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112152902829.png" alt="image-20211112152902829"></p>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112153047677.png" alt="image-20211112153047677"></p>
<ul>
<li><code>queue</code> 中有一个 <code>deque&lt;T&gt;</code>类型的<code>c</code>；</li>
<li><code>queue</code> 是容器，它容纳了 <code>deque</code>；</li>
<li><code>deque</code> 中可能有很多接口，但是<code>queue</code> 只开放这几个，<code>queue</code> 的所有功能都是通过 <code>deque</code> 来完成的，这种模式叫做 <code>Adapter</code> 模式；</li>
<li>该例子是个特例，并不是所有的<code>Composition</code> 都是这样；</li>
<li>有了<code>Container</code>就有 <code>Componenet</code>，生命是一起的；</li>
<li>复合就是一种结构中包含其他类型/结构。</li>
</ul>
<p>内存角度解释<code>Composition</code>:</p>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112153059476.png" alt="image-20211112153059476"></p>
<ul>
<li><code>queue</code> 中的 <code>c</code> 所占的空间为 40Bytes;</li>
<li>后面的图为<code>deque</code> 内部以及 <code>Itr</code> 类内部的数据，明白地显示了为什么<code>c</code> 的大小为 40Bytes。</li>
</ul>
<h2 id="112-composition复合关系下的构造与析构"><a class="markdownIt-Anchor" href="#112-composition复合关系下的构造与析构"></a> 11.2 Composition（复合）关系下的构造与析构</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112153137944.png" alt="image-20211112153137944"></p>
<ul>
<li>左边拥有右边，左边叫做 <code>Container</code>，右边叫做 <code>Component</code>；</li>
<li>红色的部分是编译器自动加上的，并非程序员写的；</li>
<li>可能内部的 <code>Component</code> 有多个构造函数，但是编译器不知道需要哪个，所以就调用一个默认的构造函数，如果这并不是你期望的，那就需要自己在<code>Comtainer</code> 的构造函数的初始列位置写上要调用的构造函数。</li>
</ul>
<h2 id="113-delegation委托-composition-by-reference"><a class="markdownIt-Anchor" href="#113-delegation委托-composition-by-reference"></a> 11.3 Delegation（委托）.  Composition by reference.</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112153225125.png" alt="image-20211112153225125"></p>
<ul>
<li>有一个<strong>指针</strong>指向右边，需要右边的时候才创建右边；</li>
<li><code>Delegation</code> 又叫 <code>Composition by reference</code>，因为也是拥有，只是拥有的是个指针；</li>
<li>学术界不说<code>by pointer</code>，即使用的是指针传也叫 <code>by reference</code>；</li>
<li>两个类之间用指针相连，就叫做 <code>Delegation</code>；</li>
<li>因为需要右边的时候才创建右边，所以左右两边的生命不同步；</li>
<li><code>String</code>类中的所有操作都是通过<code>rep</code> 指针来实现的，这种方式叫做 <code>pointer to implementation</code>, 指针指向为<code>String</code> 实现所有功能的类；这种设计的好处是，右边无论怎么变化都不影响左边，这种手法又叫做“编译防火墙”；</li>
<li>另一个名称叫做 <code>Handle/Body</code>，左边是 <code>Handle</code>，右边是 <code>Body</code>；</li>
<li>这种做法是为了做 <code>reference counting</code>，三个 <code>String</code> 对象 <code>a</code>、<code>b</code>和<code>c</code>，都在用字符串&quot;Hello&quot;，三个对象共享 “Hello”，现在 <code>n</code> 是 3。内容一样才能共享。如果<code>a</code>想修改字符串的内容，但是不影响 <code>b</code> 和 <code>c</code>，那就拷贝一份让 <code>a</code> 去更改，然后就只剩下 <code>b</code>和 <code>c</code>共享字符串。这是<code>copy-on-write</code>，就是写的时候copy一份副本让你去写。</li>
</ul>
<h2 id="114-inheritance继承表示is-a"><a class="markdownIt-Anchor" href="#114-inheritance继承表示is-a"></a> 11.4 Inheritance(继承)，表示is-a</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112153254396.png" alt="image-20211112153254396"></p>
<ul>
<li>关系图中的 <code>T</code> 表示这是个模板类；</li>
<li>当前的例子中子类<code>_List_node</code> 中的数据成员是 <code>_M_data</code> ，但是它还涵盖了 <code>_M_next</code> 和 <code>_M_prev</code> 成员</li>
</ul>
<h2 id="115-inheritance继承关系下的构造与析构"><a class="markdownIt-Anchor" href="#115-inheritance继承关系下的构造与析构"></a> 11.5 Inheritance（继承）关系下的构造与析构</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112153321664.png" alt="image-20211112153321664"></p>
<ul>
<li>子类的对象中有父类的成分；</li>
<li>父类的析构函数必须是 <code>virtual</code> 的，否则会出现 <code>undefined behavior</code>；</li>
<li>红色部分是编译器添加的；谁先谁后已经是编译器完成了，程序员不用操心。</li>
</ul>
<h2 id="116-虚函数与多态"><a class="markdownIt-Anchor" href="#116-虚函数与多态"></a> 11.6 虚函数与多态</h2>
<h3 id="1161-inheritance继承with-span-stylecolorbluevirtualspan-functions虚函数"><a class="markdownIt-Anchor" href="#1161-inheritance继承with-span-stylecolorbluevirtualspan-functions虚函数"></a> 11.6.1 Inheritance（继承）with <span style="color:blue">virtual</span> functions（虚函数）</h3>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112153411747.png" alt="image-20211112153411747"></p>
<ul>
<li>虚函数被重新定义才能叫做<code>override</code>。</li>
</ul>
<h3 id="1162-inheritance继承with-span-stylecolorbluevirtualspan"><a class="markdownIt-Anchor" href="#1162-inheritance继承with-span-stylecolorbluevirtualspan"></a> 11.6.2 Inheritance（继承）with <span style="color:blue">virtual</span></h3>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112153452805.png" alt="image-20211112153452805"></p>
<ul>
<li>输入文件名称后，按下开始键后，程序会收到一个文件名；</li>
<li>程序要检测file name是否正确，是否有不合法字符；</li>
<li>到硬盘中查找file是否存在；</li>
<li>如果存在，则将该文件打开，并读出来。</li>
</ul>
<p>上面的这个流程所有的软件都是一样的，除了最后将文件读出来有所区别。那么，将这个框架写成模板，即<code>CDocument</code>类：</p>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112153506135.png" alt="image-20211112153506135"></p>
<figure class="highlight cpp"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">CMyDoc myDoc;</span><br><span class="line">myDoc.<span class="built_in">OnFileOpen</span>(); <span class="comment">//通过子类调用父类的函数</span></span><br></pre></td></tr></table></figure>
<p>子类中没有函数<code>OnFileOpen()</code>，<code>myDoc.OnFileOpen()</code> 的全名是 <code>CDocument::OnFileOpen(&amp;myDoc)</code>，所以才能找到 <code>CDocument</code>类中的<code>OnFileOpen</code> 函数。</p>
<p><code>CDocument::OnFileOpen(&amp;myDoc);</code>  中传入了 <code>myDoc</code> 的地址，调用<code>Serialize</code> 的时候，编译器通过<code>this</code> 进行调用，即<code>this-&gt;Serialize()</code>，而<code>this</code>就是<code>myDoc</code>， 也就调用了<code>CMyDoc</code> 类的<code>Serialized()</code> 函数。</p>
<p><code>myDoc.OnFileOpen()</code>的执行流程：</p>
<ol>
<li>调用CDocument的OnFileOpen函数；</li>
<li>在<code>OnFileOpen</code> 函数里调用了CMyDoc的 <code>Serialize()</code> 函数；</li>
<li>执行完了<code>Seriazlize()</code> 函数后又回到<code>OnFileOpen()</code> 函数中继续执行；</li>
<li><code>OnFileOpen</code> 函数执行完毕后，回到<code>main</code> 函数中。</li>
</ol>
<p>过程如图中的灰色线所示。</p>
<p>将关键动作 <code>Serialize</code> 延缓到了子类中执行。将<code>OnFileOpen()</code> 这个函数的这种做法叫做<strong>Template Method</strong>模式。</p>
<p>模拟该过程的代码：</p>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112182501634.png" alt="image-20211112182501634"></p>
<h2 id="117-inheritancecomposition-关系下的构造和析构"><a class="markdownIt-Anchor" href="#117-inheritancecomposition-关系下的构造和析构"></a> 11.7 Inheritance+Composition 关系下的构造和析构</h2>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112182805328.png" alt="image-20211112182805328"></p>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211112182836985.png" alt="image-20211112182836985"></p>
<figure class="highlight cpp"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br><span class="line">48</span><br><span class="line">49</span><br><span class="line">50</span><br><span class="line">51</span><br><span class="line">52</span><br><span class="line">53</span><br><span class="line">54</span><br><span class="line">55</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">/*************************************************************************</span></span><br><span class="line"><span class="comment">	&gt; File Name: Derived.cpp</span></span><br><span class="line"><span class="comment">	&gt; Author: Maureen</span></span><br><span class="line"><span class="comment">	&gt; Mail: Maureen@qq.com</span></span><br><span class="line"><span class="comment">	&gt; Created Time: 三 11/17 20:10:15 2021</span></span><br><span class="line"><span class="comment"> ************************************************************************/</span></span><br><span class="line"><span class="comment">//自己编写</span></span><br><span class="line"><span class="meta">#<span class="meta-keyword">include</span> <span class="meta-string">&lt;iostream&gt;</span></span></span><br><span class="line"><span class="keyword">using</span> <span class="keyword">namespace</span> std;</span><br><span class="line"></span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">Component</span> &#123;</span></span><br><span class="line"><span class="keyword">public</span>:</span><br><span class="line">    <span class="built_in">Component</span>() &#123;</span><br><span class="line">        cout &lt;&lt; <span class="string">&quot;Component constructor&quot;</span> &lt;&lt; endl;</span><br><span class="line">    &#125;</span><br><span class="line"></span><br><span class="line">    <span class="function"><span class="keyword">bool</span> <span class="title">test</span><span class="params">()</span> </span>&#123;</span><br><span class="line">        <span class="keyword">return</span> <span class="literal">true</span>;</span><br><span class="line">    &#125;</span><br><span class="line"></span><br><span class="line">    ~<span class="built_in">Component</span>() &#123;</span><br><span class="line">        cout &lt;&lt; <span class="string">&quot;Component destructor&quot;</span> &lt;&lt; endl;</span><br><span class="line">    &#125;</span><br><span class="line">&#125;;</span><br><span class="line"></span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">Base</span> &#123;</span></span><br><span class="line"><span class="keyword">public</span>:</span><br><span class="line">    <span class="built_in">Base</span>() &#123;</span><br><span class="line">        cout &lt;&lt; <span class="string">&quot;Base constructor&quot;</span> &lt;&lt; endl;</span><br><span class="line">    &#125;</span><br><span class="line"></span><br><span class="line">    ~<span class="built_in">Base</span>() &#123;</span><br><span class="line">        cout &lt;&lt; <span class="string">&quot;Base destructor&quot;</span> &lt;&lt; endl;</span><br><span class="line">    &#125;</span><br><span class="line">&#125;;</span><br><span class="line"></span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">Derived</span> :</span> <span class="keyword">public</span> Base &#123;</span><br><span class="line"><span class="keyword">protected</span>:</span><br><span class="line">    Component component;</span><br><span class="line"><span class="keyword">public</span>:</span><br><span class="line">    <span class="built_in">Derived</span>() &#123;</span><br><span class="line">        cout &lt;&lt; <span class="string">&quot;Derived constructor&quot;</span> &lt;&lt; endl;</span><br><span class="line">    &#125;</span><br><span class="line">    <span class="function"><span class="keyword">bool</span> <span class="title">test</span><span class="params">()</span> </span>&#123; <span class="keyword">return</span> component.<span class="built_in">test</span>(); &#125;</span><br><span class="line"></span><br><span class="line">    ~<span class="built_in">Derived</span>() &#123;</span><br><span class="line">        cout &lt;&lt; <span class="string">&quot;Derived destructor&quot;</span> &lt;&lt; endl;</span><br><span class="line">    &#125;</span><br><span class="line">&#125;;</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="function"><span class="keyword">int</span> <span class="title">main</span><span class="params">()</span> </span>&#123;</span><br><span class="line">    Derived obj;</span><br><span class="line">    <span class="keyword">return</span> <span class="number">0</span>;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>
<p>运行结果：</p>
<figure class="highlight delphi"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line">Base <span class="function"><span class="keyword">constructor</span></span></span><br><span class="line"><span class="function"><span class="title">Component</span> <span class="title">constructor</span></span></span><br><span class="line"><span class="function"><span class="title">Derived</span> <span class="title">constructor</span></span></span><br><span class="line"><span class="function"><span class="title">Derived</span> <span class="title">destructor</span></span></span><br><span class="line"><span class="function"><span class="title">Component</span> <span class="title">destructor</span></span></span><br><span class="line"><span class="function"><span class="title">Base</span> <span class="title">destructor</span></span></span><br></pre></td></tr></table></figure>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211117202637564.png" alt="image-20211117202637564"></p>
<p><code>Derived</code> 的构造函数先调用 <code>Component</code> 的 default 构造函数，然后调用 <code>Base</code> 的 default 构造函数，然后才执行自己。</p>
<figure class="highlight cpp"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">Derived::<span class="built_in">Derived</span>(...): <span class="built_in">Component</span>(), <span class="built_in">Base</span>() &#123;...&#125;</span><br></pre></td></tr></table></figure>
<p><code>Derived</code> 的析构函数首先执行自己，然后调用 <code>Base</code> 的析构函数，然后调用 <code>Component</code> 的析构函数。</p>
<figure class="highlight cpp"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">Derived::~<span class="built_in">Derived</span>(...) &#123;... ~<span class="built_in">Base</span>(), ~<span class="built_in">Component</span>() &#125;</span><br></pre></td></tr></table></figure>
<p>示例程序：</p>
<figure class="highlight cpp"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br><span class="line">48</span><br><span class="line">49</span><br><span class="line">50</span><br><span class="line">51</span><br><span class="line">52</span><br><span class="line">53</span><br><span class="line">54</span><br><span class="line">55</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">/*************************************************************************</span></span><br><span class="line"><span class="comment">	&gt; File Name: test2.cpp</span></span><br><span class="line"><span class="comment">	&gt; Author: Maureen</span></span><br><span class="line"><span class="comment">	&gt; Mail: Maureen@qq.com</span></span><br><span class="line"><span class="comment">	&gt; Created Time: 三 11/17 20:21:15 2021</span></span><br><span class="line"><span class="comment"> ************************************************************************/</span></span><br><span class="line"><span class="comment">//自己编写</span></span><br><span class="line"><span class="meta">#<span class="meta-keyword">include</span> <span class="meta-string">&lt;iostream&gt;</span></span></span><br><span class="line"><span class="keyword">using</span> <span class="keyword">namespace</span> std;</span><br><span class="line"></span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">Component</span> &#123;</span></span><br><span class="line"><span class="keyword">public</span>:</span><br><span class="line">    <span class="built_in">Component</span>() &#123;</span><br><span class="line">        cout &lt;&lt; <span class="string">&quot;Component constructor&quot;</span> &lt;&lt; endl;</span><br><span class="line">    &#125;</span><br><span class="line"></span><br><span class="line">    <span class="function"><span class="keyword">void</span> <span class="title">test</span><span class="params">()</span> </span>&#123;</span><br><span class="line">        cout &lt;&lt; <span class="string">&quot;Component test function&quot;</span> &lt;&lt; endl;</span><br><span class="line">    &#125;</span><br><span class="line"></span><br><span class="line">    ~<span class="built_in">Component</span>() &#123;</span><br><span class="line">        cout &lt;&lt; <span class="string">&quot;Component destructor&quot;</span> &lt;&lt; endl;</span><br><span class="line">    &#125;</span><br><span class="line">&#125;;</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">Base</span> &#123;</span></span><br><span class="line"><span class="keyword">public</span>:</span><br><span class="line">    Component comp;</span><br><span class="line">    <span class="built_in">Base</span>() &#123;</span><br><span class="line">        cout &lt;&lt; <span class="string">&quot;Base constructor&quot;</span> &lt;&lt; endl;</span><br><span class="line">    &#125;</span><br><span class="line"></span><br><span class="line">    <span class="function"><span class="keyword">void</span> <span class="title">test</span><span class="params">()</span> </span>&#123; comp.<span class="built_in">test</span>(); &#125;</span><br><span class="line"></span><br><span class="line">    ~<span class="built_in">Base</span>() &#123;</span><br><span class="line">        cout &lt;&lt; <span class="string">&quot;Base destructor&quot;</span> &lt;&lt; endl;</span><br><span class="line">    &#125;</span><br><span class="line">&#125;;</span><br><span class="line"></span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">Derived</span> :</span> <span class="keyword">public</span> Base &#123;</span><br><span class="line"><span class="keyword">public</span>:</span><br><span class="line">    <span class="built_in">Derived</span>() &#123;</span><br><span class="line">        cout &lt;&lt; <span class="string">&quot;Derived constructor&quot;</span> &lt;&lt; endl;</span><br><span class="line">    &#125;</span><br><span class="line"></span><br><span class="line">    ~<span class="built_in">Derived</span>() &#123;</span><br><span class="line">        cout &lt;&lt; <span class="string">&quot;Derived destructor&quot;</span> &lt;&lt; endl;</span><br><span class="line">    &#125;</span><br><span class="line">&#125;;</span><br><span class="line"></span><br><span class="line"><span class="function"><span class="keyword">int</span> <span class="title">main</span><span class="params">()</span> </span>&#123;</span><br><span class="line">    Derived obj;</span><br><span class="line">    <span class="keyword">return</span> <span class="number">0</span>;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>
<p>运行结果：</p>
<figure class="highlight shell"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line">maureen@localhost 03.inheritance_and_composition % ./a.out                                                                                                                                                                                                                  </span><br><span class="line">Component constructor</span><br><span class="line">Base constructor</span><br><span class="line">Derived constructor</span><br><span class="line">Derived destructor</span><br><span class="line">Base destructor</span><br><span class="line">Component destructor</span><br></pre></td></tr></table></figure>
<h2 id="118-delegation委托-inheritance继承"><a class="markdownIt-Anchor" href="#118-delegation委托-inheritance继承"></a> 11.8 Delegation(委托) + Inheritance(继承)</h2>
<p>需要解决的问题：</p>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211117203523015.png" alt="image-20211117203523015"></p>
<ul>
<li>四个窗口在看同一份文件/或者同一份数据，三种不同的view查看；</li>
<li>当某个窗口的数据发生变化时，其它的也要跟着改变，因为只有一份数据</li>
</ul>
<p>设计方案：</p>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211117203358710.png" alt="image-20211117203358710"></p>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211117213319789.png" alt="image-20211117213319789"></p>
<h2 id="119-委托相关设计"><a class="markdownIt-Anchor" href="#119-委托相关设计"></a> 11.9 委托相关设计</h2>
<ul>
<li>如何设计一个FileSystem或者WindowSystem？</li>
</ul>
<p>通常使用 <code>Composite</code> 这种设计模式：</p>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211117213758788.png" alt="image-20211117213758788"></p>
<ul>
<li>创建未来可能出现的类的对象</li>
</ul>
<p>通常使用 <code>Prototype</code> 模式，子类创建自己类型的原型（对象），并将该对象放到父类中，使得父类能够看见；且子类中都要写函数<code>clone</code>，用于 <code>new</code> 自己。</p>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211117214713958.png" alt="image-20211117214713958"></p>
<p>源码：</p>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211117220007249.png" alt="image-20211117220007249"></p>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211117220050313.png" alt="image-20211117220050313"></p>
<p><img src="https://gitee.com/maureen-liu/typora-image/raw/master/typora-image/image-20211117220106586.png" alt="image-20211117220106586"></p>
<p>相关设计模式来源《Design Patterns Explained Simply》</p>
<p>源码：<a target="_blank" rel="noopener" href="https://sourcemaking.com/design_patterns/prototype/cpp/3">https://sourcemaking.com/design_patterns/prototype/cpp/3</a></p>
<figure class="highlight cpp"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br><span class="line">48</span><br><span class="line">49</span><br><span class="line">50</span><br><span class="line">51</span><br><span class="line">52</span><br><span class="line">53</span><br><span class="line">54</span><br><span class="line">55</span><br><span class="line">56</span><br><span class="line">57</span><br><span class="line">58</span><br><span class="line">59</span><br><span class="line">60</span><br><span class="line">61</span><br><span class="line">62</span><br><span class="line">63</span><br><span class="line">64</span><br><span class="line">65</span><br><span class="line">66</span><br><span class="line">67</span><br><span class="line">68</span><br><span class="line">69</span><br><span class="line">70</span><br><span class="line">71</span><br><span class="line">72</span><br><span class="line">73</span><br><span class="line">74</span><br><span class="line">75</span><br><span class="line">76</span><br><span class="line">77</span><br><span class="line">78</span><br><span class="line">79</span><br><span class="line">80</span><br><span class="line">81</span><br><span class="line">82</span><br><span class="line">83</span><br><span class="line">84</span><br><span class="line">85</span><br><span class="line">86</span><br><span class="line">87</span><br><span class="line">88</span><br><span class="line">89</span><br><span class="line">90</span><br><span class="line">91</span><br><span class="line">92</span><br><span class="line">93</span><br><span class="line">94</span><br><span class="line">95</span><br><span class="line">96</span><br><span class="line">97</span><br><span class="line">98</span><br><span class="line">99</span><br><span class="line">100</span><br><span class="line">101</span><br><span class="line">102</span><br><span class="line">103</span><br><span class="line">104</span><br><span class="line">105</span><br><span class="line">106</span><br><span class="line">107</span><br><span class="line">108</span><br><span class="line">109</span><br><span class="line">110</span><br><span class="line">111</span><br><span class="line">112</span><br><span class="line">113</span><br><span class="line">114</span><br><span class="line">115</span><br><span class="line">116</span><br><span class="line">117</span><br><span class="line">118</span><br><span class="line">119</span><br><span class="line">120</span><br><span class="line">121</span><br><span class="line">122</span><br><span class="line">123</span><br><span class="line">124</span><br><span class="line">125</span><br><span class="line">126</span><br><span class="line">127</span><br><span class="line">128</span><br><span class="line">129</span><br><span class="line">130</span><br><span class="line">131</span><br><span class="line">132</span><br><span class="line">133</span><br><span class="line">134</span><br><span class="line">135</span><br><span class="line">136</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">#<span class="meta-keyword">include</span> <span class="meta-string">&lt;iostream&gt;</span></span></span><br><span class="line"></span><br><span class="line"><span class="class"><span class="keyword">enum</span> <span class="title">imageType</span></span></span><br><span class="line"><span class="class">&#123;</span></span><br><span class="line">  LSAT, SPOT</span><br><span class="line">&#125;;</span><br><span class="line"></span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">Image</span></span></span><br><span class="line"><span class="class">&#123;</span></span><br><span class="line">  <span class="keyword">public</span>:</span><br><span class="line">    <span class="function"><span class="keyword">virtual</span> <span class="keyword">void</span> <span class="title">draw</span><span class="params">()</span> </span>= <span class="number">0</span>;</span><br><span class="line">    <span class="function"><span class="keyword">static</span> Image *<span class="title">findAndClone</span><span class="params">(imageType)</span></span>;</span><br><span class="line">  <span class="keyword">protected</span>:</span><br><span class="line">    <span class="function"><span class="keyword">virtual</span> imageType <span class="title">returnType</span><span class="params">()</span> </span>= <span class="number">0</span>;</span><br><span class="line">    <span class="function"><span class="keyword">virtual</span> Image *<span class="title">clone</span><span class="params">()</span> </span>= <span class="number">0</span>;</span><br><span class="line">    <span class="comment">// As each subclass of Image is declared, it registers its prototype</span></span><br><span class="line">    <span class="function"><span class="keyword">static</span> <span class="keyword">void</span> <span class="title">addPrototype</span><span class="params">(Image *image)</span></span></span><br><span class="line"><span class="function">    </span>&#123;</span><br><span class="line">        _prototypes[_nextSlot++] = image;</span><br><span class="line">    &#125;</span><br><span class="line">  <span class="keyword">private</span>:</span><br><span class="line">    <span class="comment">// addPrototype() saves each registered prototype here</span></span><br><span class="line">    <span class="keyword">static</span> Image *_prototypes[<span class="number">10</span>];</span><br><span class="line">    <span class="keyword">static</span> <span class="keyword">int</span> _nextSlot;</span><br><span class="line">&#125;;</span><br><span class="line"></span><br><span class="line">Image *Image::_prototypes[];</span><br><span class="line"><span class="keyword">int</span> Image::_nextSlot;</span><br><span class="line"></span><br><span class="line"><span class="comment">// Client calls this public static member function when it needs an instance</span></span><br><span class="line"><span class="comment">// of an Image subclass</span></span><br><span class="line"><span class="function">Image *<span class="title">Image::findAndClone</span><span class="params">(imageType type)</span></span></span><br><span class="line"><span class="function"></span>&#123;</span><br><span class="line">  <span class="keyword">for</span> (<span class="keyword">int</span> i = <span class="number">0</span>; i &lt; _nextSlot; i++)</span><br><span class="line">    <span class="keyword">if</span> (_prototypes[i]-&gt;<span class="built_in">returnType</span>() == type)</span><br><span class="line">      <span class="keyword">return</span> _prototypes[i]-&gt;<span class="built_in">clone</span>();</span><br><span class="line">  <span class="keyword">return</span> <span class="literal">NULL</span>;</span><br><span class="line">&#125;</span><br><span class="line"></span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">LandSatImage</span>:</span> <span class="keyword">public</span> Image</span><br><span class="line">&#123;</span><br><span class="line">  <span class="keyword">public</span>:</span><br><span class="line">    <span class="function">imageType <span class="title">returnType</span><span class="params">()</span></span></span><br><span class="line"><span class="function">    </span>&#123;</span><br><span class="line">        <span class="keyword">return</span> LSAT;</span><br><span class="line">    &#125;</span><br><span class="line">    <span class="function"><span class="keyword">void</span> <span class="title">draw</span><span class="params">()</span></span></span><br><span class="line"><span class="function">    </span>&#123;</span><br><span class="line">        std::cout &lt;&lt; <span class="string">&quot;LandSatImage::draw &quot;</span> &lt;&lt; _id &lt;&lt; std::endl;</span><br><span class="line">    &#125;</span><br><span class="line">    <span class="comment">// When clone() is called, call the one-argument ctor with a dummy arg</span></span><br><span class="line">    <span class="function">Image *<span class="title">clone</span><span class="params">()</span></span></span><br><span class="line"><span class="function">    </span>&#123;</span><br><span class="line">        <span class="keyword">return</span> <span class="keyword">new</span> <span class="built_in">LandSatImage</span>(<span class="number">1</span>);</span><br><span class="line">    &#125;</span><br><span class="line">  <span class="keyword">protected</span>:</span><br><span class="line">    <span class="comment">// This is only called from clone()</span></span><br><span class="line">    <span class="built_in">LandSatImage</span>(<span class="keyword">int</span> dummy)</span><br><span class="line">    &#123;</span><br><span class="line">        _id = _count++;</span><br><span class="line">    &#125;</span><br><span class="line">  <span class="keyword">private</span>:</span><br><span class="line">    <span class="comment">// Mechanism for initializing an Image subclass - this causes the</span></span><br><span class="line">    <span class="comment">// default ctor to be called, which registers the subclass&#x27;s prototype</span></span><br><span class="line">    <span class="keyword">static</span> LandSatImage _landSatImage;</span><br><span class="line">    <span class="comment">// This is only called when the private static data member is initiated</span></span><br><span class="line">    <span class="built_in">LandSatImage</span>()</span><br><span class="line">    &#123;</span><br><span class="line">        <span class="built_in">addPrototype</span>(<span class="keyword">this</span>);</span><br><span class="line">    &#125;</span><br><span class="line">    <span class="comment">// Nominal &quot;state&quot; per instance mechanism</span></span><br><span class="line">    <span class="keyword">int</span> _id;</span><br><span class="line">    <span class="keyword">static</span> <span class="keyword">int</span> _count;</span><br><span class="line">&#125;;</span><br><span class="line"></span><br><span class="line"><span class="comment">// Register the subclass&#x27;s prototype</span></span><br><span class="line">LandSatImage LandSatImage::_landSatImage;</span><br><span class="line"><span class="comment">// Initialize the &quot;state&quot; per instance mechanism</span></span><br><span class="line"><span class="keyword">int</span> LandSatImage::_count = <span class="number">1</span>;</span><br><span class="line"></span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">SpotImage</span>:</span> <span class="keyword">public</span> Image</span><br><span class="line">&#123;</span><br><span class="line">  <span class="keyword">public</span>:</span><br><span class="line">    <span class="function">imageType <span class="title">returnType</span><span class="params">()</span></span></span><br><span class="line"><span class="function">    </span>&#123;</span><br><span class="line">        <span class="keyword">return</span> SPOT;</span><br><span class="line">    &#125;</span><br><span class="line">    <span class="function"><span class="keyword">void</span> <span class="title">draw</span><span class="params">()</span></span></span><br><span class="line"><span class="function">    </span>&#123;</span><br><span class="line">        std::cout &lt;&lt; <span class="string">&quot;SpotImage::draw &quot;</span> &lt;&lt; _id &lt;&lt; std::endl;</span><br><span class="line">    &#125;</span><br><span class="line">    <span class="function">Image *<span class="title">clone</span><span class="params">()</span></span></span><br><span class="line"><span class="function">    </span>&#123;</span><br><span class="line">        <span class="keyword">return</span> <span class="keyword">new</span> <span class="built_in">SpotImage</span>(<span class="number">1</span>);</span><br><span class="line">    &#125;</span><br><span class="line">  <span class="keyword">protected</span>:</span><br><span class="line">    <span class="built_in">SpotImage</span>(<span class="keyword">int</span> dummy)</span><br><span class="line">    &#123;</span><br><span class="line">        _id = _count++;</span><br><span class="line">    &#125;</span><br><span class="line">  <span class="keyword">private</span>:</span><br><span class="line">    <span class="built_in">SpotImage</span>()</span><br><span class="line">    &#123;</span><br><span class="line">        <span class="built_in">addPrototype</span>(<span class="keyword">this</span>);</span><br><span class="line">    &#125;</span><br><span class="line">    <span class="keyword">static</span> SpotImage _spotImage;</span><br><span class="line">    <span class="keyword">int</span> _id;</span><br><span class="line">    <span class="keyword">static</span> <span class="keyword">int</span> _count;</span><br><span class="line">&#125;;</span><br><span class="line"></span><br><span class="line">SpotImage SpotImage::_spotImage;</span><br><span class="line"><span class="keyword">int</span> SpotImage::_count = <span class="number">1</span>;</span><br><span class="line"></span><br><span class="line"><span class="comment">// Simulated stream of creation requests</span></span><br><span class="line"><span class="keyword">const</span> <span class="keyword">int</span> NUM_IMAGES = <span class="number">8</span>;</span><br><span class="line">imageType input[NUM_IMAGES] =</span><br><span class="line">&#123;</span><br><span class="line">  LSAT, LSAT, LSAT, SPOT, LSAT, SPOT, SPOT, LSAT</span><br><span class="line">&#125;;</span><br><span class="line"></span><br><span class="line"><span class="function"><span class="keyword">int</span> <span class="title">main</span><span class="params">()</span></span></span><br><span class="line"><span class="function"></span>&#123;</span><br><span class="line">  Image *images[NUM_IMAGES];</span><br><span class="line"></span><br><span class="line">  <span class="comment">// Given an image type, find the right prototype, and return a clone</span></span><br><span class="line">  <span class="keyword">for</span> (<span class="keyword">int</span> i = <span class="number">0</span>; i &lt; NUM_IMAGES; i++)</span><br><span class="line">    images[i] = Image::<span class="built_in">findAndClone</span>(input[i]);</span><br><span class="line"></span><br><span class="line">  <span class="comment">// Demonstrate that correct image objects have been cloned</span></span><br><span class="line">  <span class="keyword">for</span> (<span class="keyword">int</span> i = <span class="number">0</span>; i &lt; NUM_IMAGES; i++)</span><br><span class="line">    images[i]-&gt;<span class="built_in">draw</span>();</span><br><span class="line"></span><br><span class="line">  <span class="comment">// Free the dynamic memory</span></span><br><span class="line">  <span class="keyword">for</span> (<span class="keyword">int</span> i = <span class="number">0</span>; i &lt; NUM_IMAGES; i++)</span><br><span class="line">    <span class="keyword">delete</span> images[i];</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>


      <div>
        
        <div>
    
        <div style="text-align:center;color: #ccc;font-size:14px;">-------------本文结束<i class="fa fa-paw"></i>感谢您的阅读-------------</div>
    
</div>


        
      </div>

    </div>

    
    
    
        

<div>
<ul class="post-copyright">
  <li class="post-copyright-author">
    <strong>本文作者： </strong>Maureen
  </li>
  <li class="post-copyright-link">
    <strong>本文链接：</strong>
    <a href="https://maureen-liu.gitee.io/p/46598833.html" title="C++面向对象高级编程（part I)">https://maureen-liu.gitee.io/p/46598833.html</a>
  </li>
  <li class="post-copyright-license">
    <strong>版权声明： </strong>本博客所有文章除特别声明外，均采用 <a href="https://creativecommons.org/licenses/by-nc-sa/4.0/" rel="noopener" target="_blank"><i class="fab fa-fw fa-creative-commons"></i>BY-NC-SA</a> 许可协议。转载请注明出处！
  </li>
</ul>
</div>


      <footer class="post-footer">
          <div class="post-tags">
              <a href="/tags/%E4%BE%AF%E6%8D%B7/" rel="tag"># 侯捷</a>
          </div>

        


        
    <div class="post-nav">
      <div class="post-nav-item">
    <a href="/p/29d8738c.html" rel="prev" title="C++程序设计（part II）兼谈对象模型">
      <i class="fa fa-chevron-left"></i> C++程序设计（part II）兼谈对象模型
    </a></div>
      <div class="post-nav-item">
    <a href="/p/e088fcc4.html" rel="next" title="C++内存管理">
      C++内存管理 <i class="fa fa-chevron-right"></i>
    </a></div>
    </div>
      </footer>
    
  </article>
  
  
  



          </div>
          
    <div class="comments" id="valine-comments"></div>

<script>
  window.addEventListener('tabs:register', () => {
    let { activeClass } = CONFIG.comments;
    if (CONFIG.comments.storage) {
      activeClass = localStorage.getItem('comments_active') || activeClass;
    }
    if (activeClass) {
      let activeTab = document.querySelector(`a[href="#comment-${activeClass}"]`);
      if (activeTab) {
        activeTab.click();
      }
    }
  });
  if (CONFIG.comments.storage) {
    window.addEventListener('tabs:click', event => {
      if (!event.target.matches('.tabs-comment .tab-content .tab-pane')) return;
      let commentClass = event.target.classList[1];
      localStorage.setItem('comments_active', commentClass);
    });
  }
</script>

        </div>
          
  
  <div class="toggle sidebar-toggle">
    <span class="toggle-line toggle-line-first"></span>
    <span class="toggle-line toggle-line-middle"></span>
    <span class="toggle-line toggle-line-last"></span>
  </div>

  <aside class="sidebar">
    <div class="sidebar-inner">

      <ul class="sidebar-nav motion-element">
        <li class="sidebar-nav-toc">
          文章目录
        </li>
        <li class="sidebar-nav-overview">
          站点概览
        </li>
      </ul>
        
      <!--noindex-->
      <div class="post-toc-wrap sidebar-panel">
          <div class="post-toc motion-element"><ol class="nav"><li class="nav-item nav-level-1"><a class="nav-link" href="#%E4%B8%80-c%E7%BC%96%E7%A8%8B%E7%AE%80%E4%BB%8B"><span class="nav-text"> 一、C++编程简介</span></a><ol class="nav-child"><li class="nav-item nav-level-2"><a class="nav-link" href="#11-%E7%9B%AE%E6%A0%87"><span class="nav-text"> 1.1 目标</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#12-c-%E7%9A%84%E5%8E%86%E5%8F%B2"><span class="nav-text"> 1.2 C++ 的历史</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#13-c-%E6%BC%94%E5%8C%96"><span class="nav-text"> 1.3 C++ 演化</span></a></li></ol></li><li class="nav-item nav-level-1"><a class="nav-link" href="#%E4%BA%8C-%E5%A4%B4%E6%96%87%E4%BB%B6%E4%B8%8E%E7%B1%BB%E5%A3%B0%E6%98%8E"><span class="nav-text"> 二、头文件与类声明</span></a><ol class="nav-child"><li class="nav-item nav-level-2"><a class="nav-link" href="#21-c-vs-c-%E5%85%B3%E4%BA%8E%E6%95%B0%E6%8D%AE%E5%92%8C%E5%87%BD%E6%95%B0"><span class="nav-text"> 2.1 C vs. C++, 关于数据和函数</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#22-c%E5%85%B3%E4%BA%8E%E6%95%B0%E6%8D%AE%E5%92%8C%E5%87%BD%E6%95%B0"><span class="nav-text"> 2.2 C++，关于数据和函数</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#23-object-bases%E5%9F%BA%E4%BA%8E%E5%AF%B9%E8%B1%A1-vs-object-oriented%E9%9D%A2%E5%90%91%E5%AF%B9%E8%B1%A1"><span class="nav-text"> 2.3 Object Bases(基于对象) vs. Object Oriented(面向对象)</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#24-c-programs-%E4%BB%A3%E7%A0%81%E5%9F%BA%E6%9C%AC%E5%BD%A2%E5%BC%8F"><span class="nav-text"> 2.4 C++ programs 代码基本形式</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#25-header%E5%A4%B4%E6%96%87%E4%BB%B6%E7%9A%84%E5%B8%83%E5%B1%80"><span class="nav-text"> 2.5 Header(头文件)的布局</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#26-class%E7%9A%84%E5%A3%B0%E6%98%8Edeclaration"><span class="nav-text"> 2.6 class的声明（declaration）</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#27-class-template%E6%A8%A1%E6%9D%BF%E7%AE%80%E4%BB%8B"><span class="nav-text"> 2.7 class template（模板）简介</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#28-inline%E5%86%85%E8%81%94%E5%87%BD%E6%95%B0"><span class="nav-text"> 2.8 inline（内联）函数</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#29-access-level%E8%AE%BF%E9%97%AE%E7%BA%A7%E5%88%AB"><span class="nav-text"> 2.9 access level（访问级别）</span></a></li></ol></li><li class="nav-item nav-level-1"><a class="nav-link" href="#%E4%B8%89-%E6%9E%84%E9%80%A0%E5%87%BD%E6%95%B0"><span class="nav-text"> 三、构造函数</span></a><ol class="nav-child"><li class="nav-item nav-level-2"><a class="nav-link" href="#31-constructorctor%E6%9E%84%E9%80%A0%E5%87%BD%E6%95%B0"><span class="nav-text"> 3.1 constructor（ctor，构造函数）</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#32-%E6%9E%84%E9%80%A0%E5%87%BD%E6%95%B0%E5%8F%AF%E4%BB%A5%E9%87%8D%E8%BD%BDoverloading"><span class="nav-text"> 3.2 构造函数可以重载（overloading）</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#33-constructorctors%E6%9E%84%E9%80%A0%E5%87%BD%E6%95%B0%E8%A2%AB%E6%94%BE%E5%9C%A8-span-stylecolorredprivatespan-%E5%8C%BA"><span class="nav-text"> 3.3 constructor(ctors,构造函数）被放在 private 区</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#34-const-member-functions%E5%B8%B8%E9%87%8F%E6%88%90%E5%91%98%E5%87%BD%E6%95%B0"><span class="nav-text"> 3.4 const member functions（常量成员函数）</span></a></li></ol></li><li class="nav-item nav-level-1"><a class="nav-link" href="#%E5%9B%9B-%E5%8F%82%E6%95%B0%E4%BC%A0%E9%80%92%E4%B8%8E%E8%BF%94%E5%9B%9E%E5%80%BC"><span class="nav-text"> 四、参数传递与返回值</span></a><ol class="nav-child"><li class="nav-item nav-level-2"><a class="nav-link" href="#41-%E5%8F%82%E6%95%B0%E4%BC%A0%E9%80%92upass-span-stylecolorblueby-valuespanu-vs-upass-span-stylecolorblueby-referencespanuspan-stylecolorgreyto-constspan"><span class="nav-text"> 4.1 参数传递：pass by value vs. pass by reference（to const）</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#42-%E8%BF%94%E5%9B%9E%E5%80%BC%E4%BC%A0%E9%80%92return-span-stylecolorblueby-valuespan-vs-return-span-stylecolorblueby-referencespan-span-stylecolorgreyto-constspan"><span class="nav-text"> 4.2 返回值传递：return by value vs. return by reference (to const)</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#43-friend%E5%8F%8B%E5%85%83"><span class="nav-text"> 4.3 friend(友元)</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#44-%E7%9B%B8%E5%90%8C-class-%E7%9A%84%E5%90%84%E4%B8%AA-objects-%E4%BA%92%E4%B8%BA-friends%E5%8F%8B%E5%85%83"><span class="nav-text"> 4.4 相同 class 的各个 objects 互为 friends（友元）</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#45-class-body-%E5%A4%96%E7%9A%84%E5%90%84%E7%A7%8D%E5%AE%9A%E4%B9%89definitions"><span class="nav-text"> 4.5 class body 外的各种定义（definitions）</span></a></li></ol></li><li class="nav-item nav-level-1"><a class="nav-link" href="#%E4%BA%94-%E6%93%8D%E4%BD%9C%E7%AC%A6%E9%87%8D%E8%BD%BD%E4%B8%8E%E4%B8%B4%E6%97%B6%E5%AF%B9%E8%B1%A1"><span class="nav-text"> 五、操作符重载与临时对象</span></a><ol class="nav-child"><li class="nav-item nav-level-2"><a class="nav-link" href="#51-operator-overloading-%E6%93%8D%E4%BD%9C%E7%AC%A6%E9%87%8D%E8%BD%BD-1%E6%88%90%E5%91%98%E5%87%BD%E6%95%B0this"><span class="nav-text"> 5.1 operator overloading （操作符重载-1，成员函数）this</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#52-return-by-reference%E8%AF%AD%E6%B3%95%E5%88%86%E6%9E%90"><span class="nav-text"> 5.2 return by reference语法分析</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#53-class-body-%E4%B9%8B%E5%A4%96%E7%9A%84%E9%87%8D%E5%AE%9A%E4%B9%89"><span class="nav-text"> 5.3 class body 之外的重定义</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#54-operator-overloading%E6%93%8D%E4%BD%9C%E7%AC%A6%E9%87%8D%E8%BD%BD-2-%E9%9D%9E%E6%88%90%E5%91%98%E5%87%BD%E6%95%B0%E6%97%A0this"><span class="nav-text"> 5.4 operator overloading（操作符重载-2， 非成员函数）无this</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#55-temp-object%E4%B8%B4%E6%97%B6%E5%AF%B9%E8%B1%A1"><span class="nav-text"> 5.5 temp object临时对象</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#56-%E5%B0%8F%E7%BB%93"><span class="nav-text"> 5.6 小结</span></a></li></ol></li><li class="nav-item nav-level-1"><a class="nav-link" href="#%E5%85%AD-%E5%A4%8D%E4%B9%A0complex%E7%B1%BB%E7%9A%84%E5%AE%9E%E7%8E%B0%E8%BF%87%E7%A8%8B"><span class="nav-text"> 六、复习Complex类的实现过程</span></a></li><li class="nav-item nav-level-1"><a class="nav-link" href="#%E4%B8%83-%E4%B8%89%E5%A4%A7%E5%87%BD%E6%95%B0%E6%8B%B7%E8%B4%9D%E6%9E%84%E9%80%A0%E6%8B%B7%E8%B4%9D%E8%B5%8B%E5%80%BC%E6%9E%90%E6%9E%84"><span class="nav-text"> 七、三大函数：拷贝构造，拷贝赋值，析构</span></a><ol class="nav-child"><li class="nav-item nav-level-2"><a class="nav-link" href="#71-class%E7%9A%84%E4%B8%A4%E4%B8%AA%E7%BB%8F%E5%85%B8%E5%88%86%E7%B1%BB"><span class="nav-text"> 7.1 class的两个经典分类</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#72-string-class"><span class="nav-text"> 7.2 String class</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#73-big-three-%E4%B8%89%E4%B8%AA%E7%89%B9%E6%AE%8A%E5%87%BD%E6%95%B0"><span class="nav-text"> 7.3 Big Three, 三个特殊函数</span></a><ol class="nav-child"><li class="nav-item nav-level-3"><a class="nav-link" href="#731-ctor%E5%92%8Cdtor%E6%9E%84%E9%80%A0%E5%87%BD%E6%95%B0%E5%92%8C%E6%9E%90%E6%9E%84%E5%87%BD%E6%95%B0"><span class="nav-text"> 7.3.1 ctor和dtor（构造函数和析构函数）</span></a></li><li class="nav-item nav-level-3"><a class="nav-link" href="#732-class-with-pointer-members-%E5%BF%85%E9%A1%BB%E6%9C%89-copy-ctor%E5%92%8C-copy-op"><span class="nav-text"> 7.3.2 class with pointer members 必须有 copy ctor和 copy op&#x3D;</span></a></li><li class="nav-item nav-level-3"><a class="nav-link" href="#733-copy-ctor%E6%8B%B7%E8%B4%9D%E6%9E%84%E9%80%A0%E5%87%BD%E6%95%B0"><span class="nav-text"> 7.3.3 copy ctor（拷贝构造函数）</span></a></li><li class="nav-item nav-level-3"><a class="nav-link" href="#734-copy-assignment-operator%E6%8B%B7%E8%B4%9D%E8%B5%8B%E5%80%BC%E5%87%BD%E6%95%B0"><span class="nav-text"> 7.3.4 copy assignment operator（拷贝赋值函数）</span></a></li><li class="nav-item nav-level-3"><a class="nav-link" href="#735-output%E5%87%BD%E6%95%B0"><span class="nav-text"> 7.3.5 output函数</span></a></li></ol></li></ol></li><li class="nav-item nav-level-1"><a class="nav-link" href="#%E5%85%AB-%E5%A0%86-%E6%A0%88%E4%B8%8E%E5%86%85%E5%AD%98%E7%AE%A1%E7%90%86"><span class="nav-text"> 八、堆、栈与内存管理</span></a><ol class="nav-child"><li class="nav-item nav-level-2"><a class="nav-link" href="#81-%E6%89%80%E8%B0%93-stack%E6%A0%88%E6%89%80%E8%B0%93-heap%E5%A0%86"><span class="nav-text"> 8.1 所谓 stack（栈），所谓 heap（堆）</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#82-stack-objects%E7%9A%84%E7%94%9F%E5%91%BD%E6%9C%9F"><span class="nav-text"> 8.2 stack objects的生命期</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#83-static-local-objects%E7%9A%84%E7%94%9F%E5%91%BD%E6%9C%9F"><span class="nav-text"> 8.3 static local objects的生命期</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#84-global-objects%E7%9A%84%E7%94%9F%E5%91%BD%E6%9C%9F"><span class="nav-text"> 8.4 global objects的生命期</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#85-heap-objects%E7%9A%84%E7%94%9F%E5%91%BD%E5%91%A8%E6%9C%9F"><span class="nav-text"> 8.5 heap objects的生命周期</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#86-new%E5%85%88%E5%88%86%E9%85%8Dmemory%E5%86%8D%E8%B0%83%E7%94%A8ctor"><span class="nav-text"> 8.6 new：先分配memory，再调用ctor</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#87-delete%E5%85%88%E8%B0%83%E7%94%A8dtor%E5%86%8D%E9%87%8A%E6%94%BEmemory"><span class="nav-text"> 8.7 delete：先调用dtor，再释放memory</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#88-new%E5%85%88%E5%88%86%E9%85%8Dmemory%E5%86%8D%E8%B0%83%E7%94%A8ctor"><span class="nav-text"> 8.8 new：先分配memory，再调用ctor</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#89-delete%E5%85%88%E8%B0%83%E7%94%A8dtor%E5%86%8D%E9%87%8A%E6%94%BEmemory"><span class="nav-text"> 8.9 delete：先调用dtor，再释放memory</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#810-%E5%8A%A8%E6%80%81%E5%88%86%E9%85%8D%E6%89%80%E5%BE%97%E7%9A%84%E5%86%85%E5%AD%98%E5%9D%97memory-blockin-vc"><span class="nav-text"> 8.10 动态分配所得的内存块（memory block），in VC</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#811-%E5%8A%A8%E6%80%81%E5%88%86%E9%85%8D%E7%9A%84array"><span class="nav-text"> 8.11 动态分配的array</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#812-array-new-%E4%B8%80%E5%AE%9A%E8%A6%81%E6%90%AD%E9%85%8D-array-delete"><span class="nav-text"> 8.12 array new 一定要搭配 array delete</span></a></li></ol></li><li class="nav-item nav-level-1"><a class="nav-link" href="#%E4%B9%9D-%E5%A4%8D%E4%B9%A0string%E7%B1%BB%E7%9A%84%E5%AE%9E%E7%8E%B0%E8%BF%87%E7%A8%8B"><span class="nav-text"> 九、复习String类的实现过程</span></a></li><li class="nav-item nav-level-1"><a class="nav-link" href="#%E5%8D%81-%E6%89%A9%E5%B1%95%E8%A1%A5%E5%85%85%E7%B1%BB%E6%A8%A1%E6%9D%BF-%E5%87%BD%E6%95%B0%E6%A8%A1%E6%9D%BF%E5%8F%8A%E5%85%B6%E5%AE%83"><span class="nav-text"> 十、扩展补充：类模板、函数模板及其它</span></a><ol class="nav-child"><li class="nav-item nav-level-2"><a class="nav-link" href="#101-%E8%BF%9B%E4%B8%80%E6%AD%A5%E8%A1%A5%E5%85%85static"><span class="nav-text"> 10.1 进一步补充：static</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#102-%E8%BF%9B%E4%B8%80%E6%AD%A5%E8%A1%A5%E5%85%85%E6%8A%8Actors%E6%94%BE%E5%9C%A8private%E5%8C%BA"><span class="nav-text"> 10.2 进一步补充：把ctors放在private区</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#103-%E8%BF%9B%E4%B8%80%E6%AD%A5%E8%A1%A5%E5%85%85cout"><span class="nav-text"> 10.3 进一步补充：cout</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#104-%E8%BF%9B%E4%B8%80%E6%AD%A5%E8%A1%A5%E5%85%85class-template%E7%B1%BB%E6%A8%A1%E6%9D%BF"><span class="nav-text"> 10.4 进一步补充：class template，类模板</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#105-%E8%BF%9B%E4%B8%80%E6%AD%A5%E8%A1%A5%E5%85%85function-template%E5%87%BD%E6%95%B0%E6%A8%A1%E6%9D%BF"><span class="nav-text"> 10.5 进一步补充：function template，函数模板</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#106-%E8%BF%9B%E4%B8%80%E6%AD%A5%E8%A1%A5%E5%85%85namespace"><span class="nav-text"> 10.6 进一步补充：namespace</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#107-%E6%9B%B4%E5%A4%9A%E7%BB%86%E8%8A%82%E4%B8%8E%E6%B7%B1%E5%85%A5"><span class="nav-text"> 10.7 更多细节与深入</span></a></li></ol></li><li class="nav-item nav-level-1"><a class="nav-link" href="#%E5%8D%81%E4%B8%80-%E7%BB%84%E5%90%88%E4%B8%8E%E7%BB%A7%E6%89%BF"><span class="nav-text"> 十一、组合与继承</span></a><ol class="nav-child"><li class="nav-item nav-level-2"><a class="nav-link" href="#111-composition%E5%A4%8D%E5%90%88%E8%A1%A8%E7%A4%BAhas-a"><span class="nav-text"> 11.1 Composition（复合），表示has-a</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#112-composition%E5%A4%8D%E5%90%88%E5%85%B3%E7%B3%BB%E4%B8%8B%E7%9A%84%E6%9E%84%E9%80%A0%E4%B8%8E%E6%9E%90%E6%9E%84"><span class="nav-text"> 11.2 Composition（复合）关系下的构造与析构</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#113-delegation%E5%A7%94%E6%89%98-composition-by-reference"><span class="nav-text"> 11.3 Delegation（委托）.  Composition by reference.</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#114-inheritance%E7%BB%A7%E6%89%BF%E8%A1%A8%E7%A4%BAis-a"><span class="nav-text"> 11.4 Inheritance(继承)，表示is-a</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#115-inheritance%E7%BB%A7%E6%89%BF%E5%85%B3%E7%B3%BB%E4%B8%8B%E7%9A%84%E6%9E%84%E9%80%A0%E4%B8%8E%E6%9E%90%E6%9E%84"><span class="nav-text"> 11.5 Inheritance（继承）关系下的构造与析构</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#116-%E8%99%9A%E5%87%BD%E6%95%B0%E4%B8%8E%E5%A4%9A%E6%80%81"><span class="nav-text"> 11.6 虚函数与多态</span></a><ol class="nav-child"><li class="nav-item nav-level-3"><a class="nav-link" href="#1161-inheritance%E7%BB%A7%E6%89%BFwith-span-stylecolorbluevirtualspan-functions%E8%99%9A%E5%87%BD%E6%95%B0"><span class="nav-text"> 11.6.1 Inheritance（继承）with virtual functions（虚函数）</span></a></li><li class="nav-item nav-level-3"><a class="nav-link" href="#1162-inheritance%E7%BB%A7%E6%89%BFwith-span-stylecolorbluevirtualspan"><span class="nav-text"> 11.6.2 Inheritance（继承）with virtual</span></a></li></ol></li><li class="nav-item nav-level-2"><a class="nav-link" href="#117-inheritancecomposition-%E5%85%B3%E7%B3%BB%E4%B8%8B%E7%9A%84%E6%9E%84%E9%80%A0%E5%92%8C%E6%9E%90%E6%9E%84"><span class="nav-text"> 11.7 Inheritance+Composition 关系下的构造和析构</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#118-delegation%E5%A7%94%E6%89%98-inheritance%E7%BB%A7%E6%89%BF"><span class="nav-text"> 11.8 Delegation(委托) + Inheritance(继承)</span></a></li><li class="nav-item nav-level-2"><a class="nav-link" href="#119-%E5%A7%94%E6%89%98%E7%9B%B8%E5%85%B3%E8%AE%BE%E8%AE%A1"><span class="nav-text"> 11.9 委托相关设计</span></a></li></ol></li></ol></div>
      </div>
      <!--/noindex-->
     
      <div class="site-overview-wrap sidebar-panel">
        <div class="site-author motion-element" itemprop="author" itemscope itemtype="http://schema.org/Person">
    <img class="site-author-image" itemprop="image" alt="Maureen"
      src="/images/stan.jpeg">
  <p class="site-author-name" itemprop="name">Maureen</p>
  <div class="site-description" itemprop="description">心之所向，素履以往</div>
</div>
<div class="site-state-wrap motion-element">
  <nav class="site-state">
      <div class="site-state-item site-state-posts">
          <a href="/archives/">
        
          <span class="site-state-item-count">7</span>
          <span class="site-state-item-name">日志</span>
        </a>
      </div>
      <div class="site-state-item site-state-categories">
            <a href="/categories/">
          
        <span class="site-state-item-count">7</span>
        <span class="site-state-item-name">分类</span></a>
      </div>
      <div class="site-state-item site-state-tags">
            <a href="/tags/">
          
        <span class="site-state-item-count">2</span>
        <span class="site-state-item-name">标签</span></a>
      </div>
  </nav>
</div>
  <div class="links-of-author motion-element">
      <span class="links-of-author-item">
        <a href="https://github.com/maureenLiu" title="GitHub → https:&#x2F;&#x2F;github.com&#x2F;maureenLiu" rel="noopener" target="_blank"><i class="fab fa-github fa-fw"></i>GitHub</a>
      </span>
      <span class="links-of-author-item">
        <a href="https://blog.csdn.net/u011386173?spm=1000.2115.3001.5343" title="CSDN → https:&#x2F;&#x2F;blog.csdn.net&#x2F;u011386173?spm&#x3D;1000.2115.3001.5343" rel="noopener" target="_blank"><i class="crosshairs fa-fw"></i>CSDN</a>
      </span>
      <span class="links-of-author-item">
        <a href="mailto:maureen@qq.com" title="E-Mail → mailto:maureen@qq.com" rel="noopener" target="_blank"><i class="fa fa-envelope fa-fw"></i>E-Mail</a>
      </span>
  </div>
  <div class="cc-license motion-element" itemprop="license">
    <a href="https://creativecommons.org/licenses/by-nc-sa/4.0/" class="cc-opacity" rel="noopener" target="_blank"><img src="/images/cc-by-nc-sa.svg" alt="Creative Commons"></a>
  </div>



      </div>

        <div id="music163player"> 
            <iframe frameborder="no" border="0" marginwidth="0" marginheight="0" width=330 height=86 src="//music.163.com/outchain/player?type=2&id=1475596788&auto=1&height=66"></iframe> 
        </div>
        <div class="back-to-top motion-element">
          <i class="fa fa-arrow-up"></i>
          <span>0%</span>
        </div>

    </div>
  </aside>
  <div id="sidebar-dimmer"></div>


      </div>
    </main>

    <footer class="footer">
      <div class="footer-inner">
        

        

<div class="copyright">
  
  &copy; 2021 – 
  <span itemprop="copyrightYear">2022</span>
  <span class="with-love">
    <i class="fa fa-heart"></i>
  </span>
  <span class="author" itemprop="copyrightHolder">Maureen</span>
    <span class="post-meta-divider">|</span>
    <span class="post-meta-item-icon">
      <i class="fa fa-chart-area"></i>
    </span>
      <span class="post-meta-item-text">站点总字数：</span>
    <span title="站点总字数">307k</span>
    <span class="post-meta-divider">|</span>
    <span class="post-meta-item-icon">
      <i class="fa fa-coffee"></i>
    </span>
      <span class="post-meta-item-text">站点阅读时长 &asymp;</span>
    <span title="站点阅读时长">4:39</span>
</div>

        
<div class="busuanzi-count">
  <script async src="https://busuanzi.ibruce.info/busuanzi/2.3/busuanzi.pure.mini.js"></script>
    <span class="post-meta-item" id="busuanzi_container_site_uv" style="display: none;">
      <span class="post-meta-item-icon">
        <i class="fa fa-user"></i>
      </span>
      <span class="site-uv" title="总访客量">
        <span id="busuanzi_value_site_uv"></span>
      </span>
    </span>
    <span class="post-meta-divider">|</span>
    <span class="post-meta-item" id="busuanzi_container_site_pv" style="display: none;">
      <span class="post-meta-item-icon">
        <i class="fa fa-eye"></i>
      </span>
      <span class="site-pv" title="总访问量">
        <span id="busuanzi_value_site_pv"></span>
      </span>
    </span>
</div>








      </div>
    </footer>
  </div>

  
  <script src="/lib/anime.min.js"></script>
  <script src="/lib/velocity/velocity.min.js"></script>
  <script src="/lib/velocity/velocity.ui.min.js"></script>

<script src="/js/utils.js"></script>

<script src="/js/motion.js"></script>


<script src="/js/schemes/pisces.js"></script>


<script src="/js/next-boot.js"></script>




  




  
<script src="/js/local-search.js"></script>













  

  


<script>
NexT.utils.loadComments(document.querySelector('#valine-comments'), () => {
  NexT.utils.getScript('//unpkg.com/valine/dist/Valine.min.js', () => {
    var GUEST = ['nick', 'mail', 'link'];
    var guest = 'nick,mail,link';
    guest = guest.split(',').filter(item => {
      return GUEST.includes(item);
    });
    new Valine({
      el         : '#valine-comments',
      verify     : false,
      notify     : false,
      appId      : '7A7ruXkEvS4VKjoTaajLunbw-9Nh9j0Va',
      appKey     : 'E4svxhhfVsrC9eCyM8YfT8uq',
      placeholder: "Just go go",
      avatar     : 'mm',
      meta       : guest,
      pageSize   : '10' || 10,
      visitor    : false,
      lang       : 'zh-cn' || 'zh-cn',
      path       : location.pathname,
      recordIP   : false,
      serverURLs : ''
    });
  }, window.Valine);
});
</script>

<script src="/live2dw/lib/L2Dwidget.min.js?094cbace49a39548bed64abff5988b05"></script><script>L2Dwidget.init({"log":false,"pluginJsPath":"lib/","pluginModelPath":"assets/","pluginRootPath":"live2dw/","tagMode":false});</script></body>
</html>

<!-- 页面点击小红心 -->
<script type="text/javascript" src="/js/clicklove.js"></script>
